在不使用PowerShell中的正则表达式的情况下,检查字符串中是否包含数组的项

时间:2018-09-18 19:25:41

标签: powershell

我有这个字符串变量:

$path = "C:\Windows"

我有这个字符串数组:

$badDir = "windows",
        "i3\ic",
        "program",
        "system",
        "pagefile.sys",
        "system",
        "swapfile.sys",
        "sourcecd", 
        "backup",
        "wwwroot",
        "users",
        "desktop",
        "documents"

我正在尝试评估$path的值中是否在数组$badDir中包含任何字符串。例如。由于我的$path值为C:\Windows,并且数组的元素之一为windows,因此应匹配“ Windows”,并且以下评估应返回true。

$badDir -Match $path.ToLower()

但是,它返回false。我在这里做错了什么?

谢谢!

2 个答案:

答案 0 :(得分:2)

What am I doing incorrectly here?

You're testing the wrong thing, and testing the wrong way round.

Since your $path value is "C:\Windows", and $badDir does not contain 'c:\windows' and does not contain (a string containing "c:\windows"), the evaluation should return false

If you don't want to use regex, you need to loop over $badDir and test each item, and then look at the results:

$path = "C:\Windows"

$badDir = "windows",
    "i3\ic",
    "program",
    "system",
    "pagefile.sys",
    "system",
    "swapfile.sys",
    "sourcecd", 
    "backup",
    "wwwroot",
    "users",
    "desktop",
    "documents"

$badDirmatch = $badDir.Where({$path.ToLower().contains($_)}, 'First').Count -as [bool]

.Where() is faster than | Where-Object and the 'first' cutoff will let it stop instantly on a match, and not test all the rest of the elements.

答案 1 :(得分:0)

$badDir -Match $path.ToLower() would compare "C:\Windows" against each element of $baddir. Since none of those are matches that is why you are getting false. The operation is muddied also since your pattern string contains regex. However this is not what you want anyway....

Pretty sure you need to compare each element of $baddirs individually against $path. I am not aware of a single operator that will do lazy matching like you expect here

($badDir | ForEach-Object{$path -match [regex]::Escape($_)}) -contains $true

$badDir elements contain regex metacharacters so we need to escape those to get true matches. Then we just check if the resulting boolean array contains any true elements. Slap that into a if block or in the pipe and you should be able to get the results you want.

There are other way to work with this depending on your actual implementation but the above should suffice.

Without Regex

Title says without regex so lets adapt what we have above to remove that part of the approach. Logic is still the same

($badDir | ForEach-Object{$path.ToLower().IndexOf("$_".ToLower()) -ge 0}) -contains $true

Check if one string is located within another. If there is we evaluate as a boolean and just like before check if one of the results are true.