首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >通过regex从行中提取特定的多个字符串

通过regex从行中提取特定的多个字符串
EN

Stack Overflow用户
提问于 2019-02-28 08:29:16
回答 3查看 87关注 0票数 2

我一直试图用.txt从PowerShell文件中的多行中提取某些值。我有一个很大的文件和所有备份,并试图提取所有这些行。

Txt文件:

代码语言:javascript
复制
Backup-ID:           hostname01
Policy:              VM_weekly
Primary Copy:        23
Expires:             1/5/2024 3:19:13 AM
Type:                4


Copy Number:        2
Fragment Size (KB): 6188832
Expires:            1/5/2024 3:19:13 AM
MediaID:            XXX122
TestID:             1222
Block:              33


Copy Number:        3
Fragment Size (KB): 6188832
Expires:            1/5/2024 3:19:13 AM
MediaID:            XXX134
TestID:             223
Block:              22
Duplicate:          N



Backup-ID:           hostname02
Policy:              VM_weekly2
Primary Copy:        24
Expires:             1/5/2024 3:19:13 AM
Type:                2


Copy Number:        2
Fragment Size (KB): 6188832
Expires:            1/5/2024 3:19:13 AM
MediaID:            XXX244
Comp:               BBB
Block:              45
Duplicate:          N


Copy Number:        3
Fragment Size (KB): 6188832
Expires:            1/5/2024 3:19:13 AM
MediaID:            XXX199
Comp:               AA
Block:              334

Copy Number:        4
Fragment Size (KB): 6188832
Expires:            1/5/2024 3:19:13 AM
MediaID:            XXX177

到目前为止我有代码:

代码语言:javascript
复制
Get-Content C:\test.txt | Select-String -Pattern 'Backup-ID: ' ,'Policy: ' ,'Primary Copy: ' ,'Expires:  ' ,'Copy Number: ' , 'Fragment Size ' ,'Expires: ' , 'MediaID:'

这就是我想要的:

代码语言:javascript
复制
hostname01,VM_weekly,23,6188832,1/5/2024 3:19:13 AM,XXX122,3,6188832,1/5/2024 3:19:13 AM,XXX134
hostname02,VM_weekly2,24,1/5/2024 3:19:13 AM,2,6188832,1/5/2024 3:19:13 AM,XXX244,3,6188832,1/5/2024 3:19:13 AM,XXX199,4,6188832,1/5/2024 3:19:13 AM,XXX177
EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2019-02-28 10:43:07

这是我的老派方法:

代码语言:javascript
复制
$line = ''
Get-Content C:\test.txt | 
    Select-String -Pattern 'Backup-ID: ' ,'Policy: ' ,'Primary Copy: ' ,'Expires:  ' ,'Copy Number: ' , 'Fragment Size ' ,'Expires: ' , 'MediaID:' |
        ForEach-Object {
            $aux = $_  -split ':',2            # only 2 substrings
            if ($aux[0] -eq 'Backup-ID') {
                if ( $line -ne '' ) { $line }  # Write-Output (current line)
                $line = $aux[1].Trim()
            } else {
                $line += ',' + $aux[1].Trim()
            }
        }
        $line                                   # Write-Output (last line)

输出

代码语言:javascript
复制
D:\PShell\SO\54921319.ps1

hostname01,VM每周,23,1/5/2024 3:19:13,2,6188832,1/5/2024 3:19,XXX122,3,6188832,1/5/2024 3:19:13上午,XXX134 hostname02,2,24,1/5/2024 3:19:13 AM,2,6188832,1/5/2024 3:19:13 AM,XXX177 244,3,6188832,1/5/2024 3:19:13 AM,XXX177 199,4,6188832,1/2024 3:19:13,XXX177

编辑:…我需要导出CSV文件…

代码语言:javascript
复制
$xArr = D:\PShell\SO\54921319.ps1
$xCsv = $xArr |  ConvertFrom-Csv -Header $(1..30|%{"a$_"})
$xcsv | Export-Csv -NoTypeInformation -Path c:\temp\result.csv

当然,你可以计算

  • -Header $(1..30|%{"a$_"})的实际上限,而不是估计的30,例如($xArr | % {$_.Split(',').Count}|Measure-Object -Maximum).Maximum
  • 甚至计算一些人类可读的头部(考虑到给定Copy Number中每个Backup-ID的属性的反复出现的名称)
票数 2
EN

Stack Overflow用户

发布于 2019-02-28 10:57:47

使用更好的模式

代码语言:javascript
复制
 $Pattern = '^Backup-ID|^Policy|^Primary Copy|^Expires|^Copy Number|^Fragment Size|^Expires|^MediaID'

和RegEx来拆分Backup-ID的输出。

代码语言:javascript
复制
(Get-Content .\test.txt|Select-String -Pattern $Pattern|Out-String) -split "(?=Backup-ID)"|ForEach-Object {
    (($_ -split "`r?`n" | %{($_ -split ":\s+",2)[1]}) -join ',').Trim(',')
}
代码语言:javascript
复制
hostname01,VM_weekly,23,1/5/2024 3:19:13 AM,2,6188832,1/5/2024 3:19:13 AM,XXX122,3,6188832,1/5/2024 3:19:13 AM,XXX134
hostname02,VM_weekly2,24,1/5/2024 3:19:13 AM,2,6188832,1/5/2024 3:19:13 AM,XXX244,3,6188832,1/5/2024 3:19:13 AM,XXX199,4,6188832,1/5/2024 3:19:13 AM,XXX177
票数 2
EN

Stack Overflow用户

发布于 2019-02-28 10:47:11

也许是这个?

代码语言:javascript
复制
& {
    $current = $null
    switch -regex -file 'C:\text.txt' {
        '^(Backup-ID|Policy|Primary Copy|Expires|Copy Number|Fragment Size \(KB\)|Expires|MediaID):\s+(.*)' {
            if ($matches[1] -eq "Backup-ID") {
                if ($current) { $current.ToString() }
                $current = [Text.StringBuilder]::new()
                [void]$current.Append($matches[2])
            }
            else {
                [void]$current.Append(",").Append($matches[2])
            }
        }
    }
    $current.ToString()
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/54921319

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档