从格式错误的csv创建新的csv(在字段之间包含LF和CR字符)

问题描述 投票:1回答:2

我有一个4列的csv文件,其中一列分布在多行中,如下所示:

Number#,Scenes,OkOrFail,Time(ms)  
1,com.mine[scenario->GRADE_1:thsi is test is request from Eol   ],OK,3613
2,com.mine[scenario->GRADE_900:MSA Harvest all losses   ],OK,1325  
14,com.mine[scenario->GRADE_450:Great lamps Entity with xbars  
Entity used SplitEnt  
Model : silicon8],OK,930  
15,com.mine[scenario->GRADE_985:request picking from the transmitter

Entity used  silicon-B.E0004  
],FAIL,728  
16,com.mine[scenario->GRADE_120:single query from Receiver with  
],OK,1245

要查看原始文件中的不可打印字符,请参阅以下内容:bad file with breaks

我想在删除Number#列后从原始csv创建一个新的csv,从Scenes列(GRADE_1,GRADE_900等)中仅提取GRADE_字符串并保留OkOrFail列。

所以新的csv将如下所示:

Scenes,OkOrFail,Time(ms)  
GRADE_1,OK,3613  
GRADE_900,OK,1325  
GRADE_450,OK,930  
GRADE_985,FAIL,728  
GRADE_120,OK,1245  

我想构建一个正则表达式来匹配整行,然后捕获我想要输出的内容将起作用。这是我的正则表达式:

^[0-9]+,.+>([A-Z_0-9]+)[^,]+(,[A-Z]+.*)

现在,在Notepad ++中,这在实际的PowerShell(使用版本5.1)中运行良好但只有前两行可以正常工作。

这是我的代码:

$origstring = "^[0-9]+,.+>([A-Z_0-9]+)[^,]+(,[A-Z]+.*)"
$testNameOnly = '$1'
$statusAndDuration = '$2'
$csvfile = "C:\small_bad.csv"

(Get-Content $csvfile) | % {
$_ = $_ -replace "Number#,", ''
$_ = $_ -replace $origstring, ($testNameOnly + $statusAndDuration)
Write-Host $_
}

输出是:

PS C:\Windows\SysWOW64\WindowsPowerShell\v1.0> 
Scenes,OkOrFail,Time(ms)
GRADE_1,OK,3613
GRADE_900,OK,1325
14,com.mine[scenario->GRADE_450:Great lamps Entity with xbars
Entity used SplitEnt
Model : silicon8],OK,930
15,com.mine[scenario->GRADE_985:request picking from the transmitter

Entity used  silicon-B.E0004
],FAIL,728
16,com.mine[scenario->GRADE_120:single query from Receiver with
],OK,1245
regex powershell csv carriage-return linefeed
2个回答
1
投票

捕获文件的整个内容(而不是逐行方法),然后执行你的正则表达式魔法:

$x = get-content -raw -path Filename1 ; $x -replace $origstring, ($testNameOnly + $statusAndDuration) | set-content -path Filename2 

3
投票

正如WiktorStribiżew所述,Get-Content将文件拆分为换行符并输出单独的行,但是你需要你的正则表达式来匹配多行,所以它无法工作。 Get-Content -Raw使它将整个文件读入包含换行符的一个字符串。

我的方法是匹配com.mine[...]文本并用双引号将其包装,从而使数据成为Import-Csv可以处理的有效CSV。

(Get-Content -Raw .\test.txt) -replace '(com\.mine\[[^\]]+\])', '"$1"' |
  ConvertFrom-Csv | Format-List

NB。假设没有办法在]部分放置com.mine[ data here ]符号。

© www.soinside.com 2019 - 2024. All rights reserved.