Powershell 快速从大文件中获取唯一记录

Powershell 快速从大文件中获取唯一记录,powershell,Powershell,我有大文件(每个文件至少20 MB),需要在其中查找字符串M(\d{10}) 以下是我正在使用的脚本: Get-Content -Path Test.log | %{ [Regex]::Matches($_, "M(\d{10})") } | %{ $_.Value } | select -Unique 这需要很长的时间和更多的CPU,请建议如何以更低的CPU使用率/更快的速度获得结果。只需测量自己(为了最小化缓存效果差异,重复第一次): 只需测量自己(为了最小化缓存效果差异,重复第一次):

我有大文件(每个文件至少20 MB),需要在其中查找字符串
M(\d{10})

以下是我正在使用的脚本:

Get-Content -Path Test.log | %{ [Regex]::Matches($_, "M(\d{10})") } | %{ $_.Value } | select -Unique
这需要很长的时间和更多的CPU,请建议如何以更低的CPU使用率/更快的速度获得结果。

只需测量自己(为了最小化缓存效果差异,重复第一次):

只需测量自己(为了最小化缓存效果差异,重复第一次):


我不会多次使用
Foreach对象
,而是使用
选择字符串

(Get-Content -Path Test.log | Select-String "(?<=M)\d{10}").Matches.Value | select -Unique

(Get Content-Path Test.log | Select String“(?我不会对每个对象多次使用
Foreach
,而是使用
Select String

(Get-Content -Path Test.log | Select-String "(?<=M)\d{10}").Matches.Value | select -Unique
(Get Content-Path Test.log | Select String)(?使用管道可能会节省内存,但速度较慢

要加快处理速度,请执行以下操作:

  • 避免使用管道,但这只是一个选项,如果您的数据作为一个整体放入内存中,这对于20MB的文件来说应该不是问题

  • 另外,直接使用.NET framework类型及其方法通常比使用cmdlet更快

将这些见解应用于您的场景(PSv3+语法):

请注意,为了方便起见,仍然使用管道,使用
Select Object-Unique
,以获得唯一的引用,但假设大部分处理(提取正则表达式匹配项)在语句的优化部分。

使用管道(可能)节省内存,但速度较慢

要加快处理速度,请执行以下操作:

  • 避免使用管道,但这只是一个选项,如果您的数据作为一个整体放入内存中,这对于20MB的文件来说应该不是问题

  • 另外,直接使用.NET framework类型及其方法通常比使用cmdlet更快

将这些见解应用于您的场景(PSv3+语法):


请注意,为了方便起见,管道仍然使用,
Select Object-Unique
,以获得唯一的引用,但假设大部分处理(提取正则表达式匹配项)都在语句的优化部分。

可能需要使用.net方法来提高效率,请看这里也许你需要使用.net方法来提高效率,看看这里,这不就是用匹配输出整行内容而不仅仅是捕获组吗?@LotPings,你是对的,我已经相应地更改了答案。另一个可以加快速度的方法是在获取内容时使用-ReadCount 0。这将在一行而不是一行读取孔文件是时候了。这不就是把整条线都和捕获组一起输出吗?@LotPings,你是对的,我已经相应地修改了答案。另一个可以加快读取速度的方法是在获取内容时使用-ReadCount 0。这将在1而不是1行读取孔文件。这是一个快速有效的:Measure命令{sls-Path Test.log“M(\d{10})”|%{$\.Matches.Groups[0].Value}{124; select-Unique}谢谢LotPings这工作很好很快:测量命令{sls-Path Test.log“M(\d{10})”|%{$\.Matches.Groups[0].Value}选择-Unique}谢谢LotPings
[regex]::Matches(
   [IO.File]::ReadAllText($PWD.ProviderPath + '/Test.log'), 
   'M\d{10}'
).Value | Select-Object -Unique