Powershell-将哈希表存储在文件中并读取其内容



作为Doug对我之前关于匿名文件的问题提出的后续建议(PowerShell-查找并替换多个模式以匿名化文件(我需要将所有哈希表值保存在单个文件中;tmp.txt";以便进一步处理。示例:在处理带有字符串的输入文件后,如:

<requestId>>qwerty-qwer12-qwer56</requestId>

tmp.txt文件包含:

qwerty-qwer12-qwer56 : RequestId-1

这是完美的。问题是,当处理许多字符串时,在tmp.txt文件中有比应该有的更多的对;RequestId-x";但是有6个。此外,当存在2个或更多个";匹配";在同一行上,只有第一个被更新/替换。你知道这些多余的线是从哪里来的吗?为什么脚本不继续检查直到同一行的末尾
这是我的测试代码:

$log = "C:log.txt"
$tmp = "C:tmp.txt"
Clear-Content $log
Clear-Content $tmp
@'
<requestId>qwerty-qwer12-qwer56</requestId>qwertykeyId>Qwd84lPhjutf7Nmwr56hJndcsjy34imNQwd84lPhjutZ7Nmwr56hJndcsjy34imNPozDr5</ABC reportId>poGd56Hnm9q3Dfer6Jh</msg:reportId>
<requestId>zxcvbn-zxcv12-zxcv56</requestId>
<requestId>qwerty-qwer12-qwer56</requestId>abcde reportId>plmkjh8765FGH4rt6As</msg:reportId>
<requestId>1234qw-12qw12-12qw56</requestId>
keyId>Qwd84lPhjutf7Nmwr56hJndcsjy34imNQwd84lPhjutZ7Nmwr56hJndcsjy34imNPozDr5</
keyId>Qwd84lPhjutf7Nmwr56hJndcsjy34imNQwd84lPhjutZ7Nmwr56hJndcsjy34imNPozDr5</
keyId>Zdjgi76Gho3sQw0ib5Mjk3sDyoq9zmGdZdjgi76Gho3sQw0ib5Mjk3sDyoq9zmGdLkJpQw</
reportId>plmkjh8765FGH4rt6As</msg:reportId>
reportId>plmkjh8765FGH4rt6As</msg:reportId>
reportId>poGd56Hnm9q3Dfer6Jh</msg:reportId>
'@ | Set-Content $log -Encoding UTF8
$requestId = @{
Count   = 1
Matches = @()
}
$keyId  = @{
Count   = 1
Matches = @()
}
$reportId  = @{
Count   = 1
Matches = @()
}
$output = switch -Regex -File $log {
'(w{6}-w{6}-w{6})' {
if(!$requestId.matches.($matches.1))
{
$req = $requestId.matches += @{$matches.1 = "RequestId-$($requestId.count)"}
$requestId.count++
$req.keys | %{ Add-Content $tmp "$_ : $($req.$_)" }
}
$_ -replace $matches.1,$requestId.matches.($matches.1)               
}
'keyId>(w{70})</' {
if(!$keyId.matches.($matches.1))
{
$kid = $keyId.matches += @{$matches.1 = "keyId-$($keyId.count)"} 
$keyId.count++
$kid.keys | %{ Add-Content $tmp "$_ : $($kid.$_)" }
}
$_ -replace $matches.1,$keyId.matches.($matches.1)        
}
'reportId>(w{19})</msg:reportId>' {
if(!$reportId.matches.($matches.1))
{
$repid = $reportId.matches += @{$matches.1 = "Report-$($reportId.count)"}
$reportId.count++
$repid.keys | %{ Add-Content $tmp "$_ : $($repid.$_)" }
}
$_ -replace $matches.1,$reportId.matches.($matches.1)
} 
default {$_}
}
$output | Set-Content $log -Encoding UTF8
Get-Content $log
Get-Content $tmp

如果你不在乎它们的发现顺序,我想如果你不想要重复的,你也不会在乎,那么最后把它们全部导出。我仍然会把它们放在";对象";表单,以便您可以轻松导入/导出它们。Csv将是数据的理想候选者。

$requestId,$keyid,$reportid | Foreach-Object {
foreach($key in $_.matches.keys)
{
[PSCustomObject]@{
Original    = $key
Replacement = $_.matches.$key
}
}
}

此示例的控制台数据输出

Original                                                               Replacement
--------                                                               -----------
qwerty-qwer12-qwer56                                                   RequestId-1
zxcvbn-zxcv12-zxcv56                                                   RequestId-2
1234qw-12qw12-12qw56                                                   RequestId-3
Qwd84lPhjutf7Nmwr56hJndcsjy34imNQwd84lPhjutZ7Nmwr56hJndcsjy34imNPozDr5 keyId-1    
Zdjgi76Gho3sQw0ib5Mjk3sDyoq9zmGdZdjgi76Gho3sQw0ib5Mjk3sDyoq9zmGdLkJpQw keyId-2    
poGd56Hnm9q3Dfer6Jh                                                    Report-1   
plmkjh8765FGH4rt6As                                                    Report-2  

只需将其导入Export-Csv

$requestId,$keyid,$reportid | Foreach-Object {
foreach($key in $_.matches.keys)
{
[PSCustomObject]@{
Original    = $key
Replacement = $_.matches.$key
}
}
} | Export-Csv $tmp -NoTypeInformation

最新更新