使用powershell对文件名和目录执行操作

使用powershell对文件名和目录执行操作,powershell,batch-file,Powershell,Batch File,我正在尝试对集合目录中的文件夹和文件名执行一些特定操作 我用“无”(“”)替换下划线(“”) 我用空(“”)替换空格(“”) 我用大写的hp和空格(“hp”)替换小写的hp(“hp”) )) 我正在用大写hp和空格(“hp”)替换大写hp(“hp”) )) 我正在用大写字母hp和空格(“hp”)替换camelcase hp(“hp”) )) 我用大写字母替换小写字母a(“a”) a(“a”)…B…C等 这是我的powershell脚本: Get-ChildItem -recurse -nam

我正在尝试对集合目录中的文件夹和文件名执行一些特定操作

  • 我用“无”(“”)替换下划线(“”)
  • 我用空(“”)替换空格(“”)
  • 我用大写的hp和空格(“hp”)替换小写的hp(“hp”) ))
  • 我正在用大写hp和空格(“hp”)替换大写hp(“hp”) ))
  • 我正在用大写字母hp和空格(“hp”)替换camelcase hp(“hp”) ))
  • 我用大写字母替换小写字母a(“a”) a(“a”)…B…C等
这是我的powershell脚本:

Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("_","") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace(" ","") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("hp","HP ") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("HP","HP ") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("Hp","HP ") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("&"," & ") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("a","A") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("b","B") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("c","C") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("d","D") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("e","E") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("f","F") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("g","G") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("h","H") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("i","I") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("j","J") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("k","K") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("l","L") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("m","M") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("n","N") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("o","O") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("p","P") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("q","Q") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("r","R") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("s","S") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("t","T") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("u","U") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("v","V") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("w","W") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("x","X") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("y","Y") }
Get-ChildItem -recurse -name | ForEach-Object { Move-Item $_ $_.replace("z","Z") }
我知道,它本质上是一堆循环

我有几个问题:

  • 上面的代码不适用于用大写字母(a-z)替换小写字母,为什么?它似乎也不是一直递归地工作。例如文件夹名称
    HP 14-Z040wm
    ,其中的文件是
    HP14-Z040wm
  • 我怎样才能最终使这个脚本更好?例如更短、更快等

  • (我也标记了批处理文件,因为我肯定会接受(我开始这么做时的第一个选择)批处理文件解决方案。

    您应该先重命名文件,然后再重命名文件夹。同时尝试这两种操作可能会使管道中的其他对象无效,并导致错误。此外,此处的重复可以使用
    -replace”\s| ;和
    .ToUpper()
    -replace`是一个正则表达式函数,我们使用它来替换所有空格和下划线,而不使用任何内容。您也可以将它们链接起来,因此我们还将替换名称开头的HP并添加到空格中

    $path = "C:\Temp"
    Get-ChildItem $path -Recurse -Directory | Rename-Item -NewName {($_.Name).ToUpper() -replace "\s|_"} -WhatIf
    Get-ChildItem $path -Recurse -File | Rename-Item -NewName {($_.Name).ToUpper() -replace "\s|_"} -WhatIf
    
    我将
    -WhatIf
    放在那里进行测试。如果此代码仅更改实体名称的大小写,则会给出一个错误,即文件/文件夹名称需要不同(中的文件夹不区分大小写)。因此,您需要先将其移动到临时文件夹中。Windows不区分大小写,因此它会看到您尝试将对象命名为相同的名称

    运行此代码时需要非常小心,因为它会将文件夹名称永久更改为临时名称。如果此过程失败,则必须手动修复损坏的文件夹。在这种情况下,请查找.bak文件夹。我的测试确实有效,但希望这只是一种预防措施。请运行自己的测试以确保安全

    $path = "C:\Temp"
    
    # Rename folders
    Get-ChildItem $path -Recurse -Directory | ForEach-Object{
        # Save the current name
        $originalName = $_.Name
        # Make sure the temp name is unique.
        $temp = Rename-Item -Path $_.FullName -NewName "$originalName.bak" -PassThru
        # Rename using the saved name and proposed changes.
        $temp | Rename-Item -NewName ($originalName.ToUpper() -replace "\s|_" -replace "^HP","HP ")
    } 
    
    Get-ChildItem $path -Recurse -File | Rename-Item -NewName {$_.Name.ToUpper() -replace "\s|_" -replace "^HP","HP "}
    

    您应该先重命名文件,然后再重命名文件夹。同时重命名这两个文件可能会使管道中的其他对象无效,并导致错误。此外,此处的重复可以使用
    -replace“\s |"和
    .ToUpper()保存
    -replace`是一个正则表达式函数,我们使用它来替换所有空格和下划线,而不使用任何内容。您也可以将这些内容链接起来,因此我们还将替换名称开头的HP并添加到空格中

    $path = "C:\Temp"
    Get-ChildItem $path -Recurse -Directory | Rename-Item -NewName {($_.Name).ToUpper() -replace "\s|_"} -WhatIf
    Get-ChildItem $path -Recurse -File | Rename-Item -NewName {($_.Name).ToUpper() -replace "\s|_"} -WhatIf
    
    我将
    -WhatIf
    放在那里进行测试。如果此代码仅更改实体名称的大小写,则会给出一个错误,即文件/文件夹名称需要不同(中的文件夹不区分大小写)。因此,您需要先将其移动到临时文件夹中。Windows不区分大小写,因此它会看到您尝试将对象命名为相同的名称

    运行此代码时需要非常小心,因为它会将文件夹名称永久更改为临时名称。如果此过程失败,则必须手动修复损坏的文件夹。在这种情况下,请查找.bak文件夹。我的测试确实有效,但希望这只是一种预防措施。请运行自己的测试以确保安全

    $path = "C:\Temp"
    
    # Rename folders
    Get-ChildItem $path -Recurse -Directory | ForEach-Object{
        # Save the current name
        $originalName = $_.Name
        # Make sure the temp name is unique.
        $temp = Rename-Item -Path $_.FullName -NewName "$originalName.bak" -PassThru
        # Rename using the saved name and proposed changes.
        $temp | Rename-Item -NewName ($originalName.ToUpper() -replace "\s|_" -replace "^HP","HP ")
    } 
    
    Get-ChildItem $path -Recurse -File | Rename-Item -NewName {$_.Name.ToUpper() -replace "\s|_" -replace "^HP","HP "}
    

    首先,只获取一次项,然后处理一次。接下来,您可以使用
    ToUpper()
    方法替换字符替换。第三,由于所有这些方法都返回字符串,因此您可以将这些方法链接在一起

    这对于文件来说非常简单:

    Get-ChildItem -Recurse -File | ForEach-Object {
        $NewName = $_.Name.ToUpper().Replace('_','').Replace(' ','').Replace('HP', 'HP ');
        Rename-Item -Path $_.FullName -NewName $NewName;
    }
    
    然而,文件夹是另一个蜡球。您不能将文件夹路径重命名为相同的名称,并且路径名称不区分大小写。因此,
    rename Item
    Move Item
    都不能单独工作。您必须使用临时文件夹名称

    以下是文件和文件夹的代码:

    #Unique name for temp folder
    $TempFolderName = [System.Guid]::NewGuid().Guid;
    
    Get-ChildItem -Recurse | ForEach-Object {
        $NewName = $_.Name.ToUpper().Replace('_','').Replace(' ','').Replace('HP', 'HP ');
        if (!$_.PSIsContainer) {
            #Regular file
            Rename-Item -Path $_.FullName -NewName $NewName;
        }
        else {
            #Get the parent folder
            $ParentFolder = Split-Path $_.FullName;
    
            #Rename folder to temp name
            Rename-Item -Path $_.FullName -NewName (Join-Path $ParentFolder $TempFolderName);
    
            #Rename temp name to folder
            Rename-Item -Path (Join-Path $ParentFolder $TempFolderName) -NewName (Join-Path $ParentFolder $NewName);
        }
    }
    

    首先,只获取一次项,然后处理一次。接下来,您可以使用
    ToUpper()
    方法替换字符替换。第三,由于所有这些方法都返回字符串,因此您可以将这些方法链接在一起

    这对于文件来说非常简单:

    Get-ChildItem -Recurse -File | ForEach-Object {
        $NewName = $_.Name.ToUpper().Replace('_','').Replace(' ','').Replace('HP', 'HP ');
        Rename-Item -Path $_.FullName -NewName $NewName;
    }
    
    然而,文件夹是另一个蜡球。您不能将文件夹路径重命名为相同的名称,并且路径名称不区分大小写。因此,
    rename Item
    Move Item
    都不能单独工作。您必须使用临时文件夹名称

    以下是文件和文件夹的代码:

    #Unique name for temp folder
    $TempFolderName = [System.Guid]::NewGuid().Guid;
    
    Get-ChildItem -Recurse | ForEach-Object {
        $NewName = $_.Name.ToUpper().Replace('_','').Replace(' ','').Replace('HP', 'HP ');
        if (!$_.PSIsContainer) {
            #Regular file
            Rename-Item -Path $_.FullName -NewName $NewName;
        }
        else {
            #Get the parent folder
            $ParentFolder = Split-Path $_.FullName;
    
            #Rename folder to temp name
            Rename-Item -Path $_.FullName -NewName (Join-Path $ParentFolder $TempFolderName);
    
            #Rename temp name to folder
            Rename-Item -Path (Join-Path $ParentFolder $TempFolderName) -NewName (Join-Path $ParentFolder $NewName);
        }
    }
    

    这当然很有趣。你试图重命名项目而不是移动正确的位置?@Matt是的,重命名。这当然很有趣。你试图重命名项目而不是移动正确的位置?@Matt是的,重命名。