次のようなファイルがあります。
7 C00000002 score: -41.156 nathvy = 49 nconfs = 2251
8 C00000002 score: -39.520 nathvy = 49 nconfs = 3129
9 C00000004 score: -38.928 nathvy = 24 nconfs = 150
10 C00000002 score: -38.454 nathvy = 49 nconfs = 9473
11 C00000004 score: -37.704 nathvy = 24 nconfs = 156
12 C00000001 score: -37.558 nathvy = 41 nconfs = 51
2 C00000002 score: -48.649 nathvy = 49 nconfs = 3878
3 C00000001 score: -44.988 nathvy = 41 nconfs = 1988
4 C00000002 score: -42.674 nathvy = 49 nconfs = 6740
5 C00000002 score: -42.453 nathvy = 49 nconfs = 4553
6 C00000002 score: -41.829 nathvy = 49 nconfs = 7559
2番目の列は、ここではソートされていない一部のIDです。たとえば、(C00000001
)など、繰り返し使用されているものもあります。それらはすべて、スコアに続く異なる番号が割り当てられています:(ほとんどの場合、番号は-
で始まります)。
私がやりたいことは:
1)2番目の列(ソートされていないID)を読み取り、常に表示される最初の列を選択します。したがって、C00000001
の場合は、score : -37.558
でオンになります。
2)一意の値が表示されたら、score:
の後の数値に基づいてソートします。つまり、最も負の数が最初の位置に、最も正の数が最後の位置になります。
入力ファイルと同じ方法で出力を出力したい(同じ構造)。
$ sort -k2,2 -u < filename | sort -k4,4n
7 C00000002 score: -41.156 nathvy = 49 nconfs = 2251
9 C00000004 score: -38.928 nathvy = 24 nconfs = 150
12 C00000001 score: -37.558 nathvy = 41 nconfs = 51
説明:
sort -k2,2 -u
:2番目の列に基づいて行を並べ替え、それらの順序を変更せず(基本的に同じ値であるため)、最初の行を保持します。sort -k4,4n
:スコアに基づいて数値順に並べ替えます(-r
を逆にする必要はありません)。GNU awk> 4.0の場合:
$ gawk '
!seen[$2] {seen[$2] = $0}
END {PROCINFO["sorted_in"] = "@val_num_asc"; for (i in seen) print seen[i]}
' file
7 C00000002 score: -41.156 nathvy = 49 nconfs = 2251
9 C00000004 score: -38.928 nathvy = 24 nconfs = 150
12 C00000001 score: -37.558 nathvy = 41 nconfs = 51
簡単に構成できる追加の単一行コマンドで貢献する
for row in $(cat tmp | awk '{print $2}' | sort | uniq); do cat tmp | grep $row | head -n 1; done | sort -r --key=4
7 C00000002 score: -41.156 nathvy = 49 nconfs = 2251
9 C00000004 score: -38.928 nathvy = 24 nconfs = 150
12 C00000001 score: -37.558 nathvy = 41 nconfs = 51