如何像 IN 语句一样使用 Powershell Where-Object
Posted
技术标签:
【中文标题】如何像 IN 语句一样使用 Powershell Where-Object【英文标题】:How to use Powershell Where-Object like an IN statement 【发布时间】:2011-11-03 00:14:31 【问题描述】:我有以下有效的代码:
foreach ($db in $svr.Databases |
where-object
$_.name -eq "testDB"
-or $_.name -eq "master"
-or $_.name -eq "model"
-or $_.name -eq "msdb" )
write-output $db.name
这是一种更清洁的方法吗?
类似:
foreach ($db in $svr.Databases |
where-object $_.name -in "testDB, master, model, msdb" )
write-output $db.name
【问题讨论】:
8kb,轻推,但我认为值得接受 Andreas Covidiot 的回答,因为它在 powershell 中使用了实际的-in
运算符
【参考方案1】:
使用-contains
运算符。喜欢:
$dbs = "testDB", "master", "model", "msdb"
foreach ($db in ($svr.Databases | where-object $dbs -contains $_.name ))
write-output $db.name
使用help about_Comparison_Operators
了解有关此运算符和其他比较运算符的更多信息。
更新:
PowerShell v3 添加了-in
运算符。原始问题中的示例适用于 v3。
【讨论】:
你不是少了一个括号吗? 是的,我确实错过了一个括号。谢谢,已修复。 原始问题中的示例不太适用 - 因为它是逗号分隔的字符串 - 而不是数组。【参考方案2】:您可以使用正则表达式:
$svr.Databases | where $_.name -match 'testDB|master|model|msdb' | foreach $db.name
【讨论】:
【参考方案3】:自 Powershell 3 以来,Powershell 有一个 -in
operator
$srv.Databases | where Name -in "master","model","msdb" | write-output $_.Name
延伸阅读:Docs on Comparison Operators > Containment Operators
【讨论】:
【参考方案4】:只是为了添加最简洁的解决方案:
([array] $svr.Databases.Name) -match '^(testDB|master|model|msdb)$'
有关 RHS regex 的说明以及对其进行试验的能力,请参阅 this regex101.com page。
以上依赖:
Member enumeration 返回$svr.Databases
集合的所有元素的.Name
属性值。
[array]
强制转换确保结果始终是一个数组,即使恰好返回一个属性值。
比较运算符(例如 -match
、regular-expression matching operator)将 数组 作为 LHS,在这种情况下它们作为 过滤器 并返回匹配元素的子数组。
相比之下,-contains
运算符和它的 PSv3+ 对应物 -in
- 两者之间的唯一区别是 操作数的顺序 - 仅支持 文字因此 single 比较值,并且只返回一个 single 布尔 ([bool]
) 值,指示比较值是否包含 (等于)数组操作数的一个元素。
注意:在本例中,literal 比较值恰好不包含正则表达式元字符,因此它们可以按原样使用;如果无法进行此假设,则必须将[regex]::Escape()
应用于比较值:
$vals = 'testDB', 'master', 'model', 'msdb'
([array] $svr.Databases.Name) -match `
('^(' + ($vals.ForEach( [regex]::Escape($_) ) -join '|') + ')$')
【讨论】:
以上是关于如何像 IN 语句一样使用 Powershell Where-Object的主要内容,如果未能解决你的问题,请参考以下文章