如何解决 Replace string 方法的区分大小写问题?

How do I get around the case sensitivity of the Replace string method?

我正在将 SCCM 中几乎所有内容的内容源移动到 DFS 共享,因此我必须更改环境中所有内容的源路径,并且在大多数情况下,我已经它编码出来。不过,我想做一些改进,以便在点击红色大按钮之前清理代码。

例如,Powershell的.Replace方法是区分大小写的,有时有人在服务器名称中只使用部分名称的大写。

\typNUMloc\ 可以是 \typNUMLOC\\TYPNUMloc\\TYPNUMLOC\。这会产生超大的 If 语句。

我的一个功能是针对驱动程序的(不是驱动程序包,我已经用类似的代码测试过,而且我只有一个输入错误的路径)。为了安全起见,红色大按钮被注释掉了。

$DriverArray = Get-CMDriver | Select CI_ID, ContentSourcePath | Where-Object {$_.ContentSourcePath -Like "\oldNUMsrv\*"}
    Foreach ($Driver in $DriverArray) {
        $DriverID = $Driver.CI_ID
        $CurrPath = $Driver.ContentSourcePath

        # Checks and replaces the root path
        If ($CurrPath -split '\' -ccontains 'path_dir') {
            $NewPath = $CurrPath.Replace("oldNUMsrv\path_dir","dfs\Path-Dir")
            #Set-CMDriver -Id $DriverID -DriverSource $NewPath
        } ElseIf ($CurrPath -split '\' -ccontains 'Path_dir') {
            $NewPath = $CurrPath.Replace("oldNUMsrv\Path_dir","dfs\Path-Dir")
            #Set-CMDriver -Id $DriverID -DriverSource $NewPath
        } ElseIf ($CurrPath -split '\' -ccontains 'Path_Dir') {
            $NewPath = $CurrPath.Replace("oldNUMsrv\Path_Dir","dfs\Path-Dir")
            #Set-CMDriver -Id $DriverID -DriverSource $NewPath
        } Else {
            Write-Host "Bad Path at $DriverID -- $CurrPath" -ForegroundColor Red
        }

        # Checks again for ones that didn't change propery (case issues)
        If ($NewPath -like "\oldNUMsrv\*") {
            Write-Host "Bad Path at $DriverID -- $CurrPath" -ForegroundColor Red
        }
    }

但是如您所知,我不需要执行大量代码。我知道,我可以使用 -replace-ireplace 方法,但我最终在我的路径中添加了额外的反斜杠 (\dfs\Path-Dir),即使使用 [regex]::escape.

如何使用不同路径的数组来匹配 $CurrPath 并执行替换?我知道它不起作用,但像这样:

If ($Array -in $CurrPath) {
    $NewPath = $CurrPath.Replace($Array, "dfs\Path-Dir"
}

我认为您的问题可能是假设您必须转义替换字符串和模式字符串。事实并非如此。由于您有控制字符(斜杠),因此您需要转义模式字符串。在它的基本形式中,你只需要做这样的事情:

PS C:\Users\Matt> "C:\temp\test\file.php" -replace [regex]::Escape("temp\test"), "another\path"
C:\another\path\file.php

但是我想更进一步。您的 if 语句都在做相对相同的事情。找到一系列字符串并用相同的东西替换它们。 -contains 也不是很必要。另请注意,默认情况下,所有这些比较运算符都不区分大小写。参见 about_comparison_operators

您可以通过构建模式字符串使用更多的正则表达式来简化所有这些。所以假设你的字符串都是唯一的(大小写无关紧要)你可以这样做:

$stringstoReplace = "oldNUMsrv1\path_dir", "oldNUMsrv2\Path_dir", "oldNUMsrv1\Path_Dir"
$regexPattern = ($stringstoReplace | ForEach-Object{[regex]::Escape($_)}) -join "|"

if($CurrPath -match $regexPattern){
     $NewPath = $CurrPath -replace $regexPattern,"new\path"
} 

您甚至不需要 if。无论如何,您都可以在所有字符串上使用 -replace 。我只留下了 if,因为你检查过是否有变化。同样,如果您只是为了解释大小写而创建所有这些语句,那么我的建议是没有实际意义的。