Regex 如何在文件中查找所有正则表达式匹配项

Regex 如何在文件中查找所有正则表达式匹配项,regex,powershell,Regex,Powershell,我有一个正则表达式列表(大约2000个)和超过一百万个html文件。我想检查每个正则表达式在每个文件上是否成功。如何在powershell上执行此操作 性能很重要,所以我不想循环使用正则表达式 我试着 它返回所有匹配项,但我还想找出,哪个模式成功,哪个不成功。我需要为每个文件构建一个成功正则表达式列表我看不出有任何方法可以通过regex集合进行foreach 这是我能想到的最好的性能: $regexes = 'pattern1','pattern2' $files = get-childitem

我有一个正则表达式列表(大约2000个)和超过一百万个html文件。我想检查每个正则表达式在每个文件上是否成功。如何在powershell上执行此操作

性能很重要,所以我不想循环使用正则表达式

我试着


它返回所有匹配项,但我还想找出,哪个模式成功,哪个不成功。我需要为每个文件构建一个成功正则表达式列表

我看不出有任何方法可以通过regex集合进行foreach

这是我能想到的最好的性能:

$regexes = 'pattern1','pattern2'
$files = get-childitem -Path  <file path> |
 select -ExpandProperty fullname

$ht = @{}

 foreach ($file in $files)
 {
   $ht[$file] = New-Object collections.arraylist
   foreach ($regex in $regexes)
    {
      if (select-string $regex $file -Quiet)
        {
          [void]$ht[$file].add($regex)
        }
    }
}

$ht
$regexes='pattern1','pattern2'
$files=获取子项-路径|
选择-ExpandProperty fullname
$ht=@{}
foreach($files中的文件)
{
$ht[$file]=新对象集合.arraylist
foreach($regex中的regex)
{
如果(选择字符串$regex$file-Quiet)
{
[void]$ht[$file]。添加($regex)
}
}
}
$ht

您可以通过使用后台作业并在作业之间划分文件集合来加快进程

您可以尝试以下方法:

$regex = "^test","e2$"  #Or use (Get-Content <path to your regex file>)
$ht = @{}

#Modify Get-Childitem to your criterias(filter, path, recurse etc.)
Get-ChildItem -Filter *.txt | Select-String -Pattern $regex | ForEach-Object { 
    $ht[$_.Path] += @($_ | Select-Object -ExpandProperty Pattern)
}
您没有指定希望输出的方式

更新:要在一行上匹配多个模式,请尝试此方法(mjolinor的答案可能比此更快)

$regex=“^test”,“e2$”#或使用(获取内容)
$ht=@{}
#将Get Childitem修改为您的标准(过滤器、路径、递归等)
$regex | ForEach对象{
$pattern=$_
获取ChildItem-Filter*.txt |选择字符串-Pattern$Pattern | ForEach对象{
$ht[$\路径]+=@($\选择对象-扩展属性模式)
}
}
更新2:我没有足够的示例来尝试它,但是由于您有如此大量的文件,您可能希望在循环模式之前尝试将文件读入内存。它可能更快

$regex = "^test","e2$"  #Or use (Get-Content <path to your regex file>)
$ht = @{}

#Modify Get-Childitem to your criterias(filter, path, recurse etc.)
Get-ChildItem -Filter *.txt | ForEach-Object {
    $text = $_ | Get-Content
    $filename = $_.FullName
    $regex | ForEach-Object {
        $text | Select-String -Pattern $_ | ForEach-Object { 
            $ht[$filename] += @($_ | Select-Object -ExpandProperty Pattern)
        }
    }
}
$regex=“^test”,“e2$”#或使用(获取内容)
$ht=@{}
#将Get Childitem修改为您的标准(过滤器、路径、递归等)
Get ChildItem-Filter*.txt | ForEach对象{
$text=$|获取内容
$filename=$\文件名
$regex | ForEach对象{
$text |选择字符串-模式$| ForEach对象{
$ht[$filename]+=@($|选择对象-扩展属性模式)
}
}
}

我试过了,但如果有多个模式,它似乎只会返回每行找到的第一个匹配项。如果给定的一行匹配多个正则表达式,它将只给出它找到的第一个匹配的模式。更新的答案。事实上,你可以有多个不同的匹配在一行是不清楚的问题。
-AllMatches
开关应该已经解决了这个问题,但它似乎无法在一系列模式中正常工作。我会将其报告为PowerShell错误/功能请求。我需要在同一行上进行多个匹配,是的-所有匹配都无法正常工作。。。感谢hintSeems处理文件的唯一方法是手动实现Aho Corasick算法更新答案。考虑到文件的数量,这可能是一个更快的解决方案。你可以看看它是否有用。:-。如果任何人同意第一个示例的问题是bug,并且是connect的成员,请在Micosoft connect上投票支持反馈
808786
$ht | Format-Table -AutoSize

Name                                               Value
----                                               -----
C:\Users\graimer\Desktop\New Text Document (2).txt {e2$}
C:\Users\graimer\Desktop\New Text Document.txt     {^test, e2$}
$regex = "^test","e2$"  #Or use (Get-Content <path to your regex file>)
$ht = @{}

#Modify Get-Childitem to your criterias(filter, path, recurse etc.)
$regex | ForEach-Object {
    $pattern = $_
    Get-ChildItem -Filter *.txt | Select-String -Pattern $pattern | ForEach-Object { 
        $ht[$_.Path] += @($_ | Select-Object -ExpandProperty Pattern)
    }
}
$regex = "^test","e2$"  #Or use (Get-Content <path to your regex file>)
$ht = @{}

#Modify Get-Childitem to your criterias(filter, path, recurse etc.)
Get-ChildItem -Filter *.txt | ForEach-Object {
    $text = $_ | Get-Content
    $filename = $_.FullName
    $regex | ForEach-Object {
        $text | Select-String -Pattern $_ | ForEach-Object { 
            $ht[$filename] += @($_ | Select-Object -ExpandProperty Pattern)
        }
    }
}