使用 Powershell 尊重原始情况重命名文件名和文件内的内容

问题描述 投票:0回答:1

有关按照解决方案此处使用 Powershell 重命名文件和文件内内容的问题。

使用下面的脚本,文件中的所有文件名和出现的位置都将被重命名。 替换不区分大小写,即无论是否出现“uvw”、“UVW”、“Uvw”等,替换都是“XYZ”。 是否可以尊重原文的情况,重新命名为“true to origin”,即 “uvw”->“xyz”,“UVW”->“XYZ”,“Uvw”->“Xyz”(默认情况下“abc_123”应该是“def_123”而不是“DEF_123”)?

$filePath = "C:\root_folder"
$include = '*.txt', '*.xml' # adapt as needed
Get-ChildItem -File $filePath -Recurse -Include $include | 
 Rename-Item -WhatIf -PassThru -NewName { $_.Name -replace 'UVW', 'XYZ' } |
 ForEach-Object {
 ($_ | Get-Content -Raw) -replace 'ABC_123', 'DEF_123' |
   Set-Content -NoNewLine -LiteralPath $_.FullName
}
powershell replace batch-rename
1个回答
0
投票

所以,这是非常低效的,但我没有找到解决方法,您需要使用匹配评估器和哈希表来将匹配的字符与其替换字符映射。

代码看起来会有所不同,具体取决于您是否使用的是存在 Replacement with a script block 的 PowerShell 7+,或者您是否使用的是 Windows PowerShell 5.1(您需要调用针对

Regex.Replace
MatchEvaluator
API)超载

  • PowerShell 7+
$evaluator = {
    $result = foreach ($char in $_.Value.GetEnumerator()) {
        $value = $map[$char.ToString()]
        if ([char]::IsUpper($char)) {
            $value.ToUpper()
            continue
        }

        $value
    }

    [string]::new($result)
}

$map = @{
    u = 'x'
    v = 'y'
    w = 'z'
}

'foo uvw bar' -replace 'uvw', $evaluator # Outputs: foo xyz bar
'foo UVW bar' -replace 'uvw', $evaluator # Outputs: foo XYZ bar
'foo Uvw bar' -replace 'uvw', $evaluator # Outputs: foo Xyz bar
  • Windows PowerShell 5.1:
$evaluator = {
    $result = foreach ($char in $args[0].Value.GetEnumerator()) {
        $value = $map[$char.ToString()]
        if ([char]::IsUpper($char)) {
            $value.ToUpper()
            continue
        }

        $value
    }

    [string]::new($result)
}

$map = @{
    u = 'x'
    v = 'y'
    w = 'z'
}

[regex]::Replace(
    'foo uvw bar',
    'uvw',
    $evaluator,
    [System.Text.RegularExpressions.RegexOptions]::IgnoreCase) # Outputs: foo xyz bar
[regex]::Replace(
    'foo UVW bar',
    'uvw',
    $evaluator,
    [System.Text.RegularExpressions.RegexOptions]::IgnoreCase) # Outputs: foo XYZ bar
[regex]::Replace(
    'foo Uvw bar',
    'uvw',
    $evaluator,
    [System.Text.RegularExpressions.RegexOptions]::IgnoreCase) # Outputs: foo Xyz bar
© www.soinside.com 2019 - 2024. All rights reserved.