将具有相同 ID 的第一列的其他列中的值相加

将具有相同 ID 的第一列的其他列中的值相加

输入的txt文件看起来像(实际的txt文件中有更多列):

target_id   length  eff_length  tot_counts  uniq_counts est_counts  eff_counts
mthl7   61  0   0   0   0   0
loqs    72  0   0   0   0   0
CG45085 58  0   0   0   0   0
CG18317 4978    1430.739479 91  0   30.333333   105.539363
CG18317 4978    1430.739479 91  0   30.333333   105.539363
CG18317 4978    1430.739479 91  0   30.333333   105.539363

对于第 1 列,当它们具有相同的 id (egCG18317) 时,我想将其余列中的值相加。所以输出看起来像:

target_id   length  eff_length  tot_counts  uniq_counts est_counts  eff_counts
mthl7   61  0   0   0   0   0
loqs    72  0   0   0   0   0
CG45085 58  0   0   0   0   0
CG18317 14934   4292.218437 273 0   90.999999   316.618089

我尝试使用如下命令:

awk -F" "
'{a[$1]+=$4;b[$1]+=$5;c[$1]+=$6;d[$1]+=$7;e[$1]+=$8;f[$1]+=$9;g[$1]+=$10;h[$1]+=$11;i[$1]+=$12;j[$1]+=$14;}END{for (i in a) print i" "a[i]" "b[i]" "c[i]" "d[i]" "e[i]" "f[i]" "g[i]" "h[i]" "i[i]" "j[i]}' temp2.txt

错误信息是:

awk: can't assign to i; it's an array name.
 input record number 7, file temp2.txt
 source line number 1

这是由于标题造成的吗?我应该如何绕过第一行?

我尝试了此处找到的类似问题的答案,但也没有成功。

答案1

$ awk 'NR==1{print;next} {for (i=2;i<=NF;i++) {a[$1][i]+=$i}} END{ \
    for (j in a) {s=j; for (i=2;i<=NF;i++) {s=s" "a[j][i]}; print s}}' file
target_id   length  eff_length  tot_counts  uniq_counts est_counts  eff_counts
mthl7 61 0 0 0 0 0
loqs 72 0 0 0 0 0
CG18317 14934 4292.22 273 0 91 316.618
CG45085 58 0 0 0 0 0

如果你想保持行的顺序相同,则需要更多的代码:

$ awk 'NR==1{print;next} {if ($1 in seen); else b[c++]=$1; seen[$1]=1; \
    for (i=2;i<=NF;i++) {a[$1][i]+=$i}} END{for (j=0;j<c;j++) {s=b[j]; \
    for (i=2;i<=NF;i++){s=s" "a[b[j]][i]}; print s}}' file | column -t
target_id  length  eff_length  tot_counts  uniq_counts  est_counts  eff_counts
mthl7      61      0           0           0            0           0
loqs       72      0           0           0            0           0
CG45085    58      0           0           0            0           0
CG18317    14934   4292.22     273         0            91          316.618

上面,我们还通过管道传输输出以column -t获得对齐的列。

适合复制和粘贴的形式的命令

为了方便查看,上述命令已分散在多个命令中。如果您想复制并粘贴命令,请改用以下版本:

awk 'NR==1{print;next} {for (i=2;i<=NF;i++) {a[$1][i]+=$i}} END{ for (j in a) {s=j; for (i=2;i<=NF;i++) {s=s" "a[j][i]}; print s}}' file

和:

awk 'NR==1{print;next} {if ($1 in seen); else b[c++]=$1; seen[$1]=1; for (i=2;i<=NF;i++) {a[$1][i]+=$i}} END{for (j=0;j<c;j++) {s=b[j]; for (i=2;i<=NF;i++){s=s" "a[b[j]][i]}; print s}}' file | column -t

非GNUawk

尝试:

awk 'NR==1{print;next} {if ($1 in seen); else b[c++]=$1; seen[$1]=1; for (i=2;i<=NF;i++) {a[$1","i]+=$i}} END{for (j=0;j<c;j++) {s=b[j]; for (i=2;i<=NF;i++){s=s" "a[b[j]","i]}; print s}}' file | column -t

相关内容