我正在合并两个csv文件。为简单起见,我仅显示相关列。两个文件中都有四列以上。
file_a.csv
col2, col6, col7, col17
a, b, c, 145
e, f, g, 101
x, y, z, 243
file_b.csv
col2, col6, col7, col17
a, b, c, 88
e, f, g, 96
x, k, l, 222
输出应如下所示:
col2, col6, col7, col17, col18
a, b, c, 145, 88
e, f, g, 101, 96
因此,当col2,col6和col7的内容匹配时,file_b的col17作为col18被添加到file_a中。
我尝试过:
awk -F, 'NR == FNR {a[$2,$6,$7] = $17;next;} {if (! (b = a[$2,$6,$7])) b = "N/A";print $0,FS,b;}' file_a.csv file_b.csv > out.csv
输出看起来像这样:
col2, col6, col7, col17,
, col18
a, b, c, 145
, 88
e, f, g, 101
, 96
所以我要添加的file_b中的第17列确实添加了,但显示在新行上。
我认为这是因为在file_a和file_b的每一行之后都有回车符。在Notepad ++中,我可以看到CRLF。但是我不能摆脱它们。另外,我宁愿不走两步:先摆脱回车,然后再合并。相反,如果我可以在合并过程中绕过回车符,它将更快。
此外,如果您能告诉我如何去除逗号分隔合并列的前后的空格,我将不胜感激。请注意,为了更好的可读性,我在各列和其他列之间用逗号隔开。实际文件中不是这样。但是合并文件中的col17与“,”和col18之间确实存在空格,我不知道为什么。
如果您坚持将其标记为重复,请在下面的评论中解释上一个问题的答案如何解决我的问题。我尝试从以前的类似问题中找出来,但失败了。
答案 0 :(得分:1)
请尝试一下(GNU awk):
awk -F, -v RS="[\r\n]+" 'NR == FNR {a[$2,$6,$7] = $17;next;} {b=a[$2,$6,$7]; print $0 FS (b? b : "N/A")}' file_a.csv file_b.csv
您遇到问题的地方:
1.回车,RS="[\r\n]+"
将把多个换行符,包括\r
和\n
视为行分隔符。请注意,如果您不想这样做,也将忽略空行,请更改为RS="\r\n"
。
2.空格,这是因为awk的默认OFS
是空格。在打印时,您使用了,
,这将在它们之间添加空格。只需使用空间,或者有时只是将它们一起写就可以了,它们会被连接起来。
答案 1 :(得分:0)
请您尝试以下。
awk -v RS="[\r\n]+" '
BEGIN{
SUBSEP=OFS=", "
}
FNR==NR{
if(FNR==1){
header=$0
}
a[$1,$2,$3]=$4
next
}
FNR==1 && FNR!=NR{
split(header,array,", ")
sub(/[a-zA-Z]+/,"",array[4])
print header,"col"array[4]+1
next
}
a[$1,$2,$3]{
print $0,a[$1,$2,$3]
}' b.csv a.csv
上面的代码做什么:
1-似乎您的Input_file中可能有回车符,所以我将\r\n
用作记录分隔符(如果要删除回车符,请尝试tr -d '\r < a.csv > temp && mv temp a.csv
并执行其他操作也是)。
2-这也会根据文件的最后一列创建标头。
答案 2 :(得分:0)
与米勒(http://johnkerl.org/miller/doc)
mlr --csv join -j col2,col6,col7 --lp l --rp r -f file_a.csv \
then unsparsify --fill-with "" \
then rename lcol17,col17,rcol17,col18 file_b.csv
你有
col2,col6,col7,col17,col18
a,b,c,145,88
e,f,g,101,96
我已经用作输入
# file_a.csv
col2,col6,col7,col17
a,b,c,145
e,f,g,101
x,y,z,243
# file_b.csv
col2,col6,col7,col17
a,b,c,88
e,f,g,96
x,k,l,222
答案 3 :(得分:0)
由于您希望在定界符,
之间获得空格,因此可以尝试使用此Perl解决方案,该解决方案在拆分时会删除空格。
答案假定文件中有\r
。我已将-vT
的{{1}}选项用于显示回车符存在
cat