按另一列的值计算一个列组的值的数量

时间:2015-01-06 16:21:10

标签: linux bash count

我有一个这样的文本文件:

asn|prefix|ip|domain
25008|85.192.184.0/21|85.192.184.59|solusi-it.com
25008|85.192.184.0/21|85.192.184.59|samtimes.ru
131755|103.31.224.0/24|103.31.224.58|karosel-ind.com
131755|103.31.224.0/24|103.31.224.58|solusi-it.com
9318|1.232.0.0/13|1.234.91.168|solusi-it.com
9318|1.232.0.0/13|1.234.91.168|es350.co.kr

有没有办法可以使用Linux Bash命令计算唯一域上的唯一ips数量,并获得这样的结果?

domain|count_ip
solusi-it.com|3
samtimes.ru|1
karosel-ind.com|1
es350.co.kr|1

3 个答案:

答案 0 :(得分:5)

使用

perl -F'\|' -lane '                                                            
    $. > 1 and $domains->{$F[3]}->{$F[2]}++;
    END{
        print "domain|count_ip";
        print $_, "|", scalar keys %{ $domains->{$_} } for keys %$domains;
    }
' file | tee new_file

这背后的想法是使用HASH的HASH

$domains->{$F[3]}->{$F[2]}++

$F[3]是域,$F[2]是IP。独特性是保证。 HASH键始终是唯一的。

输出:

domain|count_ip
es350.co.kr|1
karosel-ind.com|1
samtimes.ru|1
solusi-it.com|3

答案 1 :(得分:2)

使用awk:

~$ awk -F'|' 'NR>1{a[$NF]++}END{print "domain|count_ip";for (i in a){print i FS a[i]}}' f
domain|count_ip
karosel-ind.com|1
solusi-it.com|3
samtimes.ru|1
es350.co.kr|1

您可以使用Field separator将字段与|分开。
这不会检查ip是否已经在数组a中。

为此,您可以使用sort来测试第3和第4字段的唯一性:

~$ cat f f >f2
~$ sort -t'|' -k3,4 -u f2 | awk -F'|' 'NR>1{a[$NF]++}END{print "domain|count_ip";for (i in a){print i FS a[i]}}'
domain|count_ip
solusi-it.com|3
samtimes.ru|1
es350.co.kr|1
domain|1

答案 2 :(得分:1)

这应该这样做:

 cat data | tail -n+2 | awk -F'|' '{print  $4" "$3}' | sort | uniq | awk '{print $1}' | uniq -c | awk '{ print $2"|"$1}'

它基本上删除了标题,然后打印IP和主机,找到唯一的对{ip,host},按主机分组计算它们并格式化它们。

编辑:更正格式