이 값을 추가하여 첫 번째 열의 공통 ID를 기반으로 행을 병합하시겠습니까?

이 값을 추가하여 첫 번째 열의 공통 ID를 기반으로 행을 병합하시겠습니까?

탭으로 구분된 파일이 있습니다.

    Class      Sample_1     Sample_2      Sample_3
    A          0            0             0
    Z          0.25         0             0.75
    A|B|C      0            0             0
    A|B|C      0            1             0
    A|B|C      0.1875       0.671875      0.140625
    A|B|C      0.2739726027 0.5890410959  0.1369863014
    A|B|C|D|E  0            0.2           0.8
    A|B|C|D    0.1666666667 0.3333333333  0.5
    A|B|C|D    0.4723756906 0.179558011   0.3480662983

첫 번째 열의 ID를 기반으로 행을 병합하고 병합하는 동안 값을 추가하고 싶습니다.

Class       Sample_1        Sample_2        Sample_3
A           0               0               0
Z           0.25            0               0.75
A|B|C       0.4614726027    2.2609160959    0.2776113014
A|B|C|D|E   0               0.2             0.8
A|B|C|D     0.6390423573    0.5128913443    0.8480662983

답변1

GNU datamash의 장점은 다음과 같습니다.

$ datamash -H groupby 1 sum 2-4 < file.tsv | column -t
GroupBy(Class)  sum(Sample_1)  sum(Sample_2)  sum(Sample_3)
A               0              0              0
Z               0.25           0              0.75
A|B|C           0.4614726027   2.2609160959   0.2776113014
A|B|C|D|E       0              0.2            0.8
A|B|C|D         0.6390423573   0.5128913443   0.8480662983

또는 GNU awk에서 2D 배열을 사용합니다(배열 순회 순서는 보장되지 않으므로 출력 라인이 반드시 입력과 동일한 순서일 필요는 없습니다).

$ gawk '
    BEGIN{getline; print} 
    {for(i=2;i<=4;i++) a[$1][i] += $i} 
    END {
      for(k in a){printf k; for(i=2;i<=4;i++) printf "\t%s", a[k][i]; printf "\n"}
    }' file.tsv | column -t
Class      Sample_1  Sample_2  Sample_3
A          0         0         0
A|B|C      0.461473  2.26092   0.277611
A|B|C|D    0.639042  0.512891  0.848066
A|B|C|D|E  0         0.2       0.8
Z          0.25      0         0.75

column -t참고: 시각적 서식 지정을 위해 파이프를 추가했습니다.

답변2

이는 다음 방법으로 수행됩니다.

for i in `awk 'NR>1{if (!seen[$1]++){print $1}}' p.txt`; do awk -v i="$i" '$1 == i{print $0}' p.txt| awk -v i="$i" 'BEGIN{sum=0;hum=0;rum=0}{sum=sum+$2;hum=hum+$3;rum=rum+$4}END {print i,sum,hum,rum}'|awk '{printf "%s%14s%20s%20s\n",$1,$2,$3,$4}'; done| sed '1i  Class      Sample_1           Sample_2       Sample_3'

산출

Class      Sample_1           Sample_2       Sample_3
A             0                   0                   0
Z          0.25                   0                0.75
A|B|C      0.461473             2.26092            0.277611
A|B|C|D|E             0                 0.2                 0.8
A|B|C|D      0.639042            0.512891            0.848066

관련 정보