关于awk:无法使用uniq -c打印所有行的计数

Unable to use uniq -c to print counts for all lines

我想使用uniq来计算每行的出现次数,但不包括行首的数值(例如:0000:01:00.0)

每次发生不止一次。在某些情况下,每次出现只会发生一次。

样本输入

1
2
3
4
5
6
[root@cpod-compute-1 ~]# for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do lspci -Dm | grep $i; done
0000:01:00.0"Ethernet controller""Intel Corporation""I350 Gigabit Network Connection" -r01"Cisco Systems Inc""Device 00d5"
0000:01:00.1"Ethernet controller""Intel Corporation""I350 Gigabit Network Connection" -r01"Cisco Systems Inc""Device 00d5"
0000:0a:00.1"Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"
0000:0a:00.2"Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"
0000:0a:00.3"Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"

预期输出

1
2
2 "Ethernet controller""Intel Corporation""I350 Gigabit Network Connection" -r01"Cisco Systems Inc""Device 00d5"
3 "Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"

无效案例的示例

1
2
3
4
5
6
[root@cpod-compute-1 ~]#  for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do lspci -Dm | grep $i | awk '{$1="";print $0}' | sort | uniq -c; done
      1 "Ethernet controller""Intel Corporation""I350 Gigabit Network Connection" -r01"Cisco Systems Inc""Device 00d5"
      1 "Ethernet controller""Intel Corporation""I350 Gigabit Network Connection" -r01"Cisco Systems Inc""Device 00d5"
      1 "Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"
      1 "Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"
      1 "Ethernet controller""Intel Corporation""Ethernet Controller X710 for 10GbE SFP+" -r01"Cisco Systems Inc""Ethernet Converged NIC X710-DA"

已收集的输出
-我在收集的输出中看不到任何意外的字符。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
[root@cpod-compute-1 ~]#  for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do lspci -Dm | grep $i | awk '{$1="";print $0}' | od -c; done
0000000      "   E   t   h   e   r   n   e   t       c   o   n   t   r
0000020   o   l   l   e   r  "      "   I   n   t   e   l       C   o
0000040   r   p   o   r   a   t   i   o   n  "      "   I   3   5   0
0000060       G   i   g   a   b   i   t       N   e   t   w   o   r   k
0000100       C   o   n   n   e   c   t   i   o   n  "       -   r   0
0000120   1      "   C   i   s   c   o       S   y   s   t   e   m   s
0000140       I   n   c  "      "   D   e   v   i   c   e       0   0
0000160   d   5  "  \

0000164
0000000      "   E   t   h   e   r   n   e   t       c   o   n   t   r
0000020   o   l   l   e   r  "      "   I   n   t   e   l       C   o
0000040   r   p   o   r   a   t   i   o   n  "      "   I   3   5   0
0000060       G   i   g   a   b   i   t       N   e   t   w   o   r   k
0000100       C   o   n   n   e   c   t   i   o   n  "       -   r   0
0000120   1      "   C   i   s   c   o       S   y   s   t   e   m   s
0000140       I   n   c  "      "   D   e   v   i   c   e       0   0
0000160   d   5  "  \

0000164

[root@cpod-compute-1 ~]# for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do lspci -Dm | grep $i | awk '{$1="";print $0}' | sed -n l; done
"Ethernet controller""Intel Corporation""I350 Gigabit Network Conn\\
ection" -r01"Cisco Systems Inc""Device 00d5"$
"Ethernet controller""Intel Corporation""I350 Gigabit Network Conn\\
ection" -r01"Cisco Systems Inc""Device 00d5"$

我无法理解似乎重复的相邻行之间的区别。

请让我知道是否需要其他输出。

谢谢。


OP使用的代码为:

1
2
3
for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do
   lspci -Dm | grep $i | awk '{$1="";print $0}' | sort | uniq -c;
done

它应该读为:

1
2
3
for i in $(awk -F= '/PCI_SLOT_NAME/{print $2}' /sys/class/net/*/device/uevent); do
   lspci -Dm | grep $i | awk '{$1="";print $0}'
done | sort | uniq -c;

这两种情况之间的区别在于,在第一种情况下,您对单个命令的输出进行了排序:

1
lspci -Dm | grep $i | awk '{$1="";print $0}'

在第二种情况下,对完整的for循环的输出进行排序。

更新后的版本如下:

1
2
3
4
awk -F= '(FNR==1){ OFS=FS=(f==0 ?"=" :""); $0=$0 }
         (f==0) && /PCI_SLOT_NAME/{a[$2];next}
         ($1 in a) {$1=""; $0=$0; $1=$1; print}
        ' /sys/class/net/*/device/uevent f=1 <(lspci -Dm) | sort | uniq -c

我们现在仍然可以在awk中合并计数:

1
2
3
4
5
awk -F= '(FNR==1){ OFS=FS=(f==0 ?"=" :""); $0=$0 }
         (f==0) && /PCI_SLOT_NAME/{a[$2];next}
         ($1 in a) {$1=""; $0=$0; $1=$1; b[$0]++}
         END{for (i in b) print b[i],i}
        ' /sys/class/net/*/device/uevent f=1 <(lspci -Dm)