Linux 汇总行和汇总列
我有一个包含以下行的文件:Linux 汇总行和汇总列,linux,bash,shell,unix,awk,Linux,Bash,Shell,Unix,Awk,我有一个包含以下行的文件: 01323874;291874;-;000000000000003030;2511011999;-;000000000000000000 01323874;291874;-;000000000012920840;2511011999;+;000002910023874000 01323872;291872;-;000000000000008750;2511011999;-;000000000000008750 01323872;291872;+;00000000060
01323874;291874;-;000000000000003030;2511011999;-;000000000000000000
01323874;291874;-;000000000012920840;2511011999;+;000002910023874000
01323872;291872;-;000000000000008750;2511011999;-;000000000000008750
01323872;291872;+;000000000609396980; ;+;000000000000000000
01323778; ;-;000000000468442930; ;+;000000000000000000
01323778; ;+;000000005166500460; ;+;000000000000000000
01323778; ;-;000000000469421100;2511021000;+;000000000469421100
01323778;291778;-;000000000361156930;2511021000;-;000000000361156930
01323778; ;-;000000000186088530;2511021000;+;000000000186088530
01323778;291778;-;000000000017602470;2511021000;-;000000000017602470
我想根据第一列汇总行:
考虑到第3列中的符号(+/-),汇总第4列的值
考虑到第6列中的符号(+/-),汇总第7列的值
01323874;291874;-;000000000012923871;2511011999;+;000002910023874000
01323872;291872;+;000000000609388230;2511011999;-;000000000000008750
01323778;291778;+;000000003663788500;2511021000;+;000000000276750230
我已经成功地生成了格式良好的行,但找不到聚合它们的方法。非常感谢您的帮助
kent$ cat f
01323874;291874;-;000000000000003030;2511011999;-;000000000000000000
01323874;291874;-;000000000012920840;2511011999;+;000002910023874000
01323872;291872;-;000000000000008750;2511011999;-;000000000000008750
01323872;291872;+;000000000609396980; ;+;000000000000000000
01323778; ;-;000000000468442930; ;+;000000000000000000
01323778; ;+;000000005166500460; ;+;000000000000000000
01323778; ;-;000000000469421100;2511021000;+;000000000469421100
01323778;291778;-;000000000361156930;2511021000;-;000000000361156930
01323778; ;-;000000000186088530;2511021000;+;000000000186088530
01323778;291778;-;000000000017602470;2511021000;-;000000000017602470
输出
kent$ awk -F';' '{a[$1]=(1*$2?$2:a[$1]); b[$1]+=$3=="-"?-$4:$4;
c[$1]=(1*$5?$5:c[$1]); d[$1]+=$6=="-"?-$7:$7}
END{for(x in a)
printf "%s;%s;%s;%018d;%s;%s;%018d\n",
x,a[x],
(b[x]>0?"+":"-"),(b[x]<0?-b[x]:b[x]),c[x],
(d[x]>0?"+":"-"),(d[x]<0?-d[x]:d[x])}' f
01323872;291872;+;000000000609388230;2511011999;-;000000000000008750
01323778;291778;+;000000003663788500;2511021000;+;000000000276750230
01323874;291874;-;000000000012923870;2511011999;+;000002910023874000
kent$awk-F';“{a[$1]=(1*$2?$2:a[$1]);b[$1]+=$3==“-”?-$4:$4;
c[$1]=(1*$5?$5:c[$1]);d[$1]+=$6==“-”?-$7:$7}
结束{for(a中的x)
printf“%s;%s;%s;%018d;%s;%s;%018d\n”,
x、 a[x],
(b[x]>0?“+”:“-”,(b[x]0?“+”:“-”,(d[x]awk解决方案:
awk -F';' 'function get_sign(n){
return (n<0)? "-":"+"
}
{
a[$1]+=int($3$4); b[$1]+=int($6$7);
if ($2*1) fld2[$1]=$2; if ($5*1) fld5[$1]=$5
}
END{
for(i in a) print i, fld2[i], get_sign(a[i]),
sprintf("%018d",(a[i]>0)? a[i]:a[i]*-1), fld5[i], get_sign(b[i]),
sprintf("%018d",(b[i]>0)? b[i]:b[i]*-1)
}' OFS=';' file
function get_sign(n){…}
-函数,定义数值参数n
是正数还是负数,并返回相应的符号
到目前为止您尝试了什么?首先在这里发布您已经完成的代码。第2列和第5列如何?在每个组中,最后一列中的值是如何选择的?我没有看到任何模式。这有关系吗?仅就我个人所知,1*
的目的是什么?@fzd您将看到是否从代码中删除它。它过滤将黑色但不是空的字符串输出。如“”
@kent它很好用,谢谢,但是当第2列或第5列只包含空格时,它不会处理这个问题。例如,现在我得到了01323872;291872;+;000000000609388230;;-;0000000000000008750
但是它应该是01323872;291872;+;000000000609388230;空格;-;0000000000000008750
它很好用,谢谢,但是它不会处理第2列或第5列只包含空格的情况。例如,现在我得到01323872;291872;+;000000000609388230;;-;0000000000000008750
,但它应该是01323872;291872;+;000000000609388230;空格;-;0000000000000008750
@technopathe,这不是真的。我已经测试过这种情况,当第2列只包含空格和它给了我:01323872;;+;000000000609388230;2511101999;-;00000000000000875001323778;;+;000000003663788500;2511021000;+;000000000276750230 01323874;;;-;00000012923870;251011999;+;000002910023874000
正如预期的那样,实际上我宁愿用这种方式打印空白;******;而不是用这种方式;*指的是空白,我已经解决了ed空间问题awk-F';''函数get_-sign(n){return(n0)}a[i]:a[i]*-1,fld5[i],get_-sign(b[i]),sprintf(“%018d”,(b[i]>0)?b[i]:b[i]*-1)}OFS=“;”F1>F2
awk'BEGIN OFS=FS=“;”}{$5=sprintf(“%10s”,$5)$2=sprintf(“%10s”,$2)print}'F2>F3
,但仍需要缩小和优化
01323872;291872;+;000000000609388230;2511011999;-;000000000000008750
01323778;291778;+;000000003663788500;2511021000;+;000000000276750230
01323874;291874;-;000000000012923870;2511011999;+;000002910023874000