如何使用awk对多列(但不是全部)进行求和,并按求和值排序

时间:2015-07-22 17:55:11

标签: sorting awk

我希望我能用awk和/或排序来解决这个问题:

我有一个19列的制表符分隔文件格式如下:(以'Gene'开头的行是我的标题)

Gene  -100 -75 -50 -25  0 25 50 75 100  -100 -75 -50 -25  0 25 50 75 100
MLL      0   0   0   2  5  2  0  0   1     0   0   4   8  5  5  4  0   1
MLL2     0   0   0   7 10  7  0  0   1     0   0   0   7 10  7  0  0   1

我想对第2-10行进行求和,然后按此求和值对行进行排序,得到如下输出:

Gene  -100 -75 -50 -25  0 25 50 75 100  -100 -75 -50 -25  0 25 50 75 100
MLL2     0   0   0   7 10  7  0  0   1     0   0   0   7 10  7  0  0   1
MLL      0   0   0   2  5  2  0  0   1     0   0   4   8  5  5  4  0   1

我知道如果我能用我需要的总和值制作第20列,那么我可以使用sort来完成这项工作:

sort -nk20 file.txt

提前致谢!

1 个答案:

答案 0 :(得分:2)

两步解决方案

这会对列进行求和并将总和打印为第20列:

$ awk 'NR==1{print $0,0;next;} {s=0; for (i=2;i<=NF;i++) s+=$i; print $0,s;}' file
Gene  -100 -75 -50 -25  0 25 50 75 100  -100 -75 -50 -25  0 25 50 75 100 0
MLL      0   0   0   2  5  2  0  0   1     0   0   4   8  5  5  4  0   1 37
MLL2     0   0   0   7 10  7  0  0   1     0   0   0   7 10  7  0  0   1 50

现在可以按照您的建议将上述输出传送到sort -nk20

一步解决方案

如果你想在一步中求和并排序,如果你有GNU awk,那么使用:

$ awk 'BEGIN{PROCINFO["sorted_in"]="@val_num_asc"} NR==1{print;next} {s=0; for (i=2;i<=NF;i++) s+=$i; a[NR]=s; b[NR]=$0} END{for (i in a)print b[i]}' file

或者,写在多行:

awk 'BEGIN{PROCINFO["sorted_in"]="@val_num_asc"} 
    NR==1{print;next} 
    {s=0; for (i=2;i<=NF;i++) s+=$i; a[NR]=s; b[NR]=$0}
    END{for (i in a)print b[i]}' file

PROCINFO是GNU awk的一个功能。