我对 bash 及其语法很陌生,因此我想知道如何对列表进行排序以获取硬盘驱动器库存的总数。
示例如下。我们有许多来自不同供应商和型号的服务器和硬盘。
你会如何根据数字而不是他们名字的出现次数来将它们数在一起?
ST8000NC0002: 8
ST900MM0168: 1
ST900MM0168: 1
ST9300603SS: 3
ST9300605SS: 4
ST9500620SS: 3
WD1003FBYX: 7
WD1500HLFS: 4
WD9001BKHG: 3
WD9001BKHG: 3
WD9001BKHG: 4
WD9001BKHG: 4
期望的输出:
ST8000NC0002: 8
ST900MM0168: 2
ST9300603SS: 3
ST9300605SS: 4
ST9500620SS: 3
WD1003FBYX: 7
WD1500HLFS: 4
WD9001BKHG: 14
答案1
awk
就是为此而生的。填充data
由第一个字段( ) 索引的数组( $1
),并累积第二个字段 ( $2
) 的值。填充数组后,使用简单的for
循环输出数据。为了方便起见,通过管道输出sort
。
awk '{data[$1]+=$2} END { for( d in data ) { print d, data[d] } }' input | sort
ST8000NC0002: 8
ST900MM0168: 2
ST9300603SS: 3
ST9300605SS: 4
ST9500620SS: 3
WD1003FBYX: 7
WD1500HLFS: 4
WD9001BKHG: 14
答案2
使用 GNU datamash
:
datamash -W -g 1 sum 2 < file
-W
使用whitspace(空格/制表符)作为字段分隔符(而不是制表符)-g 1
第一个字段上的组sum 2
第二个字段的总和值(每组)
输出:
ST8000NC0002: 8
ST900MM0168: 2
ST9300603SS: 3
ST9300605SS: 4
ST9500620SS: 3
WD1003FBYX: 7
WD1500HLFS: 4
WD9001BKHG: 14
这工作正常,因为您的输入已经在第一个字段上排序。对于未排序的输入,添加选项-s
以在分组之前对输入进行排序。