gpt4 book ai didi

powershell - 如何在第一次匹配时停止管道过滤(Where-Object)

转载 作者:行者123 更新时间:2023-12-02 22:34:05 24 4
gpt4 key购买 nike

我搜索过,但还没有找到如何去做。
我正在从大文件(~2GB)中过滤数据。
我用过 Where-Object当它找到匹配项时,它会继续搜索其他有意义的匹配项。

有可能在第一场比赛中阻止它吗?

例如 (#1) :

Get-Process | Where-Object {$_.ProcessName.StartsWith("svchost")}

输出将是:
Handles  NPM(K)    PM(K)      WS(K) VM(M)   CPU(s)     Id ProcessName
------- ------ ----- ----- ----- ------ -- -----------
666 38 26928 18672 92 568 svchost
596 28 11516 16560 92 792 svchost
425 14 5364 7036 45 832 svchost
406 17 7032 8416 39 1004 svchost

我要什么是在第一次匹配后返回输出:
Handles  NPM(K)    PM(K)      WS(K) VM(M)   CPU(s)     Id ProcessName
------- ------ ----- ----- ----- ------ -- -----------
666 38 26928 18672 92 568 svchost

这是我尝试过的(也使用 Foreach-Object):
Get-Process | Where-Object {if($_.ProcessName.StartsWith("svchost")){return $_}}
Get-Process | Where-Object {if($_.ProcessName.StartsWith("svchost")){return $_;break;}}
Get-Process | ForEach-Object {if($_.ProcessName.StartsWith("svchost")){return $_}}

但它仍然返回完整的输出。
引用:
How to break Foreach loop in Powershell?
Is it possible to terminate or stop a PowerShell pipeline from within a filter

编辑(大数据问题说明):
示例(#2):
我有两个 XML:
A.xml:
<?xml version="1.0" encoding="UTF-8"?>
<Events>
<Event>
<EventData Name="Time">09/10/2017 12:54:16</EventData>
<EventData Name="WorkstationName">USER2-PC</EventData>
<EventData Name="UserName">user2</EventData>
</Event>
</Events>

B.xml:
<?xml version="1.0" encoding="UTF-8"?>
<Events>
<Event>
<EventData Name="Time">09/10/2017 14:54:16</EventData>
<EventData Name="WorkstationName">USER1-PC</EventData>
<EventData Name="UserName">user1</EventData>
</Event>
<Event>
<EventData Name="Time">09/10/2017 13:54:16</EventData>
<EventData Name="WorkstationName">USER2-PC</EventData>
<EventData Name="UserName">user2</EventData>
</Event>
... (more 100,000 events like the above two)
</Events>

这些 XML 正在作为对象加载:
$fileA = "C:\tmp\A.xml"
$a = New-Object Xml.XmlDocument
$a.Load($fileA)

$fileB = "C:\tmp\B.xml"
$b = New-Object Xml.XmlDocument
$b.Load($fileB)

然后我想搜索相同用户名的第一个匹配项:
$result = $b.Events.Event | Where-Object {
(($_.EventData | where-object {$_.Name -eq "UserName"})."#text" -eq $username)
}

$result.EventData

在这种情况下,如果我在第一个事件上匹配,那么运行其余的 99,999 个事件是浪费时间。

编辑(已解决):
阅读尼克的回答后,我没有尝试过任何新内容。
命令:
Get-Process | Where-Object {if($_.ProcessName.StartsWith("svchost")){ $_;break;}}  

确实停了 Where-Object但它不会返回该项目。
这个可以通过以下方式解决:
Get-Process | Where-Object {if($_.ProcessName.StartsWith("svchost")){ $someVar = $_;break;}}  

因此我标记了他的答案。

最佳答案

两者,Where-ObjectForEach-Object是 Cmdlet。您不能破坏 Cmdlet(命令)。你可以做的是使用关键字 foreach像这样

$process = Get-Process

foreach ($item in $process) {
if ($item.Name -eq 'svchost') {
$item
return
}
}

关于powershell - 如何在第一次匹配时停止管道过滤(Where-Object),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46327579/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com