最初の列に基づいて複数の行をマージしますが、すべての列は独立して保持する必要があります。

最初の列に基づいて複数の行をマージしますが、すべての列は独立して保持する必要があります。

1列の値に基づいて行をマージしたいと思います。私のデータは次のとおりです(タブで区切られた列)。

OG  FC_AG_NICO  FC_AG_ZEA   FC_AG_BRAS  FC_MB_NICO  FC_MB_ZEA   FC_MB_BRAS  FC_TN_NICO  FC_TN_ZEA   FC_TN_BRAS  FC_SL_NICO  FC_SL_ZEA   FC_SL_BRAS  FC_SE_NICFC_SE_ZEA  FC_SE_BRAS 
OG0004400   -0.787302663    -0.710790578    0.663333543                                             
OG0004400                                                   -1.659046364    -1.019969932    0.588969542
OG0004400                                       -0.373838773    0.277055943 0.481626213         
OG0004400               -0.360799687    -0.0958126  0.056722264                                 
OG0004400                           -1.77626686 -0.971114297    0.707963822                     
OG0004402   -0.304209641    -0.259080399    0.44366888                                              
OG0004402                                                   0.442748804 0.042958499 -0.316412832
OG0004402                                       -0.274550145    0.1933262   0.374095809         
OG0004402               0.253000346 0.338511357 -0.121760564

したがって、同じOG番号を共有する行は1つの行にマージする必要があります。列ごとに1つの値しかないため、倍精度に問題はありません。

いくつかの異なる投稿で同様の問題を扱っており、この回答が非常に役に立つと思って少し編集しました。ただし、ここではすべての値が互いに直後に記録されます。ただし、列値は同じ位置に維持されることが重要です。

awk '{if(NR!=1){a[$1]=$2"\t"a[$1]} else print $0} END {n = asorti(a, b); for (n in b) {print b[n],a[b[n]]}}'

誰でも上記のコードを編集するのに役立ちますか?

ベストアンサー1

awk 'BEGIN{FS="\t"} NR==1{print; next} {a[$1]=$1; for(i=2; i<=NF; i++){if($i!="") {f[$1,i]=$i; if(i>last[$1]){last[$1]=i}}} } END{for(j in a){printf("%s", a[j]); for(k=2; k<=last[j]; k++){printf("%s%s", FS, f[j,k])} print ""}}' file
awk 'BEGIN{FS="\t"}          # use tab as field separator
     NR==1{print; next}      # print header
     {
       a[$1]=$1              # save first column in current row
       for(i=2; i<=NF; i++){ # loop with all columns but first
         if($i!=""){         # if column not empty
           f[$1,i]=$i        # save content to array
           if(i>last[$1]){
             last[$1]=i      # save number of last element in current row
           }
         }
       }
     }
     END{
       for(j in a){
         printf("%s", a[j])           # print first element
         for(k=2; k<=last[j]; k++){   # print second to last element
           printf("%s%s", FS, f[j,k])
         }
         print ""
       }
     }' file

配列にはa最初の列が含まれています。配列には、f最初の列がない行が含まれています。配列には、last現在の行の最後の要素の位置が含まれます。

まだテストされていません。

おすすめ記事