Powershell select-string根据匹配数返回不同的值

时间:2013-09-04 20:43:35

标签: regex powershell select-string

我有一个生成的报告文件,并包含各种文件引用。 我正在使用Select-String和正则表达式匹配某些类型的文件,并对它们执行后续处理。

我遇到的困境是在零(0),一(1)或多于一(2+)个匹配时始终确定匹配的数量。这是我尝试过的:

(select-string -path $outputfilePath -pattern $regex -allmatches).matches.count

如果有0个匹配则返回“null”,如果匹配则返回“1”,如果多个匹配则返回“null”。

(select-string -path $outputfilePath -pattern $regex -allmatches).count

如果有0或1个匹配则返回“null”,如果匹配多个匹配则返回匹配数。


我对Powershell很新,但是我试图找到一种一致的方法来测试匹配的数量,无论是否有0,1或多于1的匹配。

2 个答案:

答案 0 :(得分:6)

试试这个:

$content = Get-Content $outputfilePath
($content -match $regex).Count

Powershell拥有许多Comparison Operators,可能会让您的生活更轻松。这是一个快速列表:

-eq
-ne
-gt
-ge   
-lt
-le
-Like
-NotLike
-Match
-NotMatch
-Contains
-NotContains
-In
-NotIn
-Replace

在这种情况下,-Match将$ content字符串与正则表达式$ regex匹配,输出按括号分组。此分组是字符串的集合。然后我们可以计算对象并打印出准确的匹配数。

那么为什么你的代码不按预期工作?当您进行单个匹配时,.Matches实际上会返回一个System.Text.RegularExpressions.Match对象,对于字符串“test123”,该对象看起来像这样:

Groups   : {test123}
Success  : True
Captures : {test123}
Index    : 15
Length   : 7
Value    : test123

为什么会这样?因为Microsoft.PowerShell.Commands.MatchInfo对象是Select-String返回的对象。您可以通过在单匹配输出上尝试其他属性(例如.Filename)来验证这一点。

好的,但为什么我们不能一次性获得所有比赛?这是因为多个匹配将返回多个对象,因此现在您有一个正在尝试操作的集合。该集合具有不同的类型,并且不理解.Matches。 1匹配不返回任何集合,而是理解.Matches的单个对象是!

长话短说:这些不是您正在寻找的输出!

答案 1 :(得分:2)

您可以使用array sub-expression operator @(...)始终将结果放入包含Count的集合中:

(Select-String ...)        # may return $null, one match, or a collection of matches
(Select-String ...).Count  # only succeeds for two or more matches

@(Select-String ...)       # always returns a collection of matches
@(Select-String ...).Count # always succeeds