在命令行和脚本上使用 awk 进行重复数据删除

在命令行和脚本上使用 awk 进行重复数据删除

我有一个具有以下格式的文件:

487422,Potenza
487386,Forlì-Cesena
487399,Grosseto
487425,Catanzaro
487409,Napoli
487446,Prato
495498,Fermo
487425,Catanzaro
487389,Macerata
487442,Biella
487351,Asti
487424,Cosenza
487404,Roma
487359,Como
487404,Roma
487401,Terni
487420,Brindisi
487397,Arezzo
487348,Vercelli
487382,Modena
487356,Genova
487365,Cremona
487369,Verona
487386,Forlì-Cesena

正如您所看到的,它是一个以逗号分隔且有重复项的文本。我想使用 来删除与第 1 列相关的文本awk

命令行

如果我使用 shell 界面,这就是我得到的

487422,Potenza
487386,Forlì-Cesena
487399,Grosseto
487425,Catanzaro
487409,Napoli
487446,Prato
495498,Fermo
487389,Macerata
487442,Biella
487351,Asti
487424,Cosenza
487404,Roma
487359,Como
487401,Terni
487420,Brindisi
487397,Arezzo
487348,Vercelli
487382,Modena
487356,Genova
487365,Cremona
487369,Verona

这是我对以下命令的期望

awk -F"," '!a[$1]++' filename.csv

awk脚本

如果我使用 awk 脚本编写如下

#!/bin/awk -f

BEGIN {
    FS=","
}
{
    {!a[$1]++}
}

我没有得到任何输出。是不是剧本有什么问题?为什么脚本和命令行之间的行为不同?

答案1

大括号外面!a[$1]++是一个状况{print},如果评估结果为真(非零),则会触发默认操作。

大括号内{{!a[$1]++}}是一个行动这是无条件评估的,没有副作用。去掉大括号:

#!/bin/awk -f

BEGIN {
    FS=","
}

!a[$1]++

答案2

@steeldriver 的 awk 答案是正确的,并且可能是您所需要的,但是如果您的输入变得很大,它可能会耗尽内存和/或变得相对较慢,在这种情况下,这里有一个将继续工作的装饰/排序/取消装饰方法:

nl -w1 -s, file |       # Decorate by prefixing with line numbers
sort -ut, -k2,2 |       # Sort uniquely by the real key field
sort -nt, -k1,1 |       # Sort whats left by the line numbers we added
cut -d, -f2-            # Undecorate by removing the line numbers

相关内容