給定以下 csv,具有多行欄位:
"id","text"
"1","line 1
line 2"
"2","line 1
line 2"
"1","line 1
line 2"
...顯示為:
| ID | 文本 |
|---|---|
| 1 | 第 1 行 第 2 行 |
| 2 | 第 1 行 第 2 行 |
| 1 | 第 1 行 第 2 行 |
如果我使用以下awk命令根據 id(第 1 列)從此 csv 中洗掉重復行:
awk -F, '!x[$1] ' 'file-01.csv' > 'file-01-deduped.csv'
我最終得到:
"id","text"
"1","line 1
line 2"
"2","line 1
顯示為:
| ID | 文本 |
|---|---|
| 1 | 第 1 行 第 2 行 |
| 2 | 1號線 |
這是一個過于簡單的示例,但它似乎awk不適用于多行欄位。也許我錯過了一些東西。
附加資訊:我正在根據RFC4180 標準撰寫這些csv——最值得注意的是,包含換行符、雙引號和逗號的欄位用雙引號括起來。出現在欄位中的雙引號會用前面的雙引號轉義。
另外,我在 Node/JS 中撰寫 csv,但我發現awk過去是一種非常簡單/快速的方法來洗掉非常大的檔案——盡管沒有多行欄位。
我絕不會被束縛——我awk對任何/所有建議持開放態度——只是想清楚我已經嘗試過什么。謝謝!
uj5u.com熱心網友回復:
awk 不支持 csv,因此它并不是真正適合這項作業的工具。互聯網上有一些 csv 實作,也許你可以看看它們。
你確實提到檔案很大,但如果它符合你的記憶,這是我幾周前需要的東西的變體。它是 GNU awk 使用FPAT的,所以它不是很快:
$ gawk '
BEGIN {
RS="^$" # read in whole file
FPAT="([^,\n]*)|(\"(\"\"|[^\"]) \")" # regex magic
OFS=","
}
{
for(i=1;i<NF;i =2) # iterate fields 2 at a time
if(!a[$i] ) # if first field not seen before
print $i,$(i 1) # output 2 fields
}' file
測驗資料:
"id","text"
"1","line 1
line 2"
"2","line 1
line 2"
"3"," ""line 1""
line 2"
"4",""
"5","line 1,
line 2"
"1","line 1
line 2"
輸出:
"id","text"
"1","line 1
line 2"
"2","line 1
line 2"
"3"," ""line 1""
line 2"
"4",""
"5","line 1,
line 2"
我不知道有多少種方式會讓你失望,壽。
uj5u.com熱心網友回復:
僅使用您顯示的示例,請嘗試以下awk代碼。用 GNU 撰寫和測驗awk,應該可以在任何awk.
awk -F',' '
FNR>1{
sub(/^"/,"",$2)
sub(/"$/,"",$3)
gsub(/"/,"",$1)
print $1 OFS $2 ORS " " $3
}
' <(awk '{printf("%s%s",$0!~/^"/?",":FNR>1?ORS:"",$0)} END{print ""}' Input_file)
說明:簡單的解釋是,運行 1stawk以列印單行中的所有行(無論它的行不是從哪里開始"),并將其輸出作為輸入發送到 mainawk,其中根據要求列印所需的 id 值和所有行值。
uj5u.com熱心網友回復:
我會查看 GoCSV 及其獨特的子命令。
對于您的輸入,根據文本列僅保留重復行中的第一行的命令將是:
gocsv unique -c text input.csv
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/464537.html
上一篇:如何用numpy撰寫csv檔案?
