如何使用Select-String在Powershell中返回Hashtable的(键)文件名和(值)匹配值数组?

时间:2018-04-16 13:13:05

标签: powershell

我想在目录中搜索与特定正则表达式匹配的文件,并在散列表中保存文件名和匹配值。文件可以包含多个匹配项,但每行只能匹配一个匹配项。多个文件的某些匹配值也相同,但只需要保留一个。使用foreach循环它会相当容易,但我想使用Select-String,因为根据我的经验,它更快。

我已经有了这个代码来保存数组中的匹配项:

$regex = [regex]"test\s+(\w+)"  
$path = $PSScriptRoot
$matches = Get-ChildItem $path -filter "*.txt" | Select-String -Pattern $regex | foreach-object {$_.matches.groups[1].value} | Select-Object -Unique

我知道选择文件名会使用| select name,但我如何将其与匹配值相结合?

脚本目录中包含两个文件“file1.txt”和“file2.txt”的简化示例如下所示:

FILE1.TXT

abcd
test string1

FILE2.TXT

abcd
test string1
test string2
test string3

当前$匹配:

@('string1', 'string2', 'string3')

我希望$ match匹配:

@{'file1.txt'=@('string1'); 'file2.txt'=@('string2', 'string3')}

1 个答案:

答案 0 :(得分:0)

哈希表

  • key(file)
  • value(来自文件的字符串数组,在所有文件中都是唯一的)
  • 将以下字符串添加到file1.txt以帮助进行测试
    • test string4

FILE1.TXT

abcd
test string1
test string4

FILE2.TXT

abcd
test string1
test string2
test string3

提供了变量......

$regex = [regex]"test\s+(\w+)"  
$path = $PSScriptRoot

一个班轮......

$matches = $($find = (Get-ChildItem $path -filter "*.txt" | Select-String -Pattern $regex | foreach-object {@{$_.Filename = $_.matches.groups[1].value}}) | Sort-Object Values -Unique;foreach ($file in ($find.Keys | Sort -Unique)) {@{$file = $($find | where {$_.Keys -eq $file}).Values}})

一个衬里扩大......

$matches = $(
    $find = (
        Get-ChildItem $path -filter "*.txt" | 
            Select-String -Pattern $regex | 
                foreach-object {
                    @{$_.Filename = $_.matches.groups[1].value}
                }
    ) | Sort-Object Values -Unique
    foreach ($file in ($find.Keys | Sort -Unique)) {
        @{
            $file = $(
                $find | where {$_.Keys -eq $file}
            ).Values
        }
    }
)

使用和输出

$matches.Keys
file1.txt
file2.txt

$matches.Values
string4
string1
string2
string3

$matches.'file1.txt'
string4

$matches.'file2.txt'
string1
string2
string3

$matches
Name                           Value
----                           -----
file1.txt                      {string4}
file2.txt                      {string1, string2, string3}