如何删除文件中特定的重复行?

如何删除文件中特定的重复行?

我正在寻找一种从一堆文件中删除特定行的方法,但前提是该行在该文件中出现多次。其他行应保留,即使它们是重复的。

例如,像这样的文件,我想删除重复项AAA

AAA
BBB
AAA
BBB
CCC

应该成为

AAA
BBB
BBB
CCC

我想我应该使用,sed但我不知道如何编写命令。

答案1

使用 GNU sed

sed '0,/^AAA$/b;//d'

也就是说,让所有内容通过(b像 a 一样分支continue)直到第一AAA行(从第 0 行(甚至在第一行之前)和第一个匹配的行/^AAA$/(可能是第一行)),然后是剩余的行,删除所有出现的AAA(空//模式重复使用最后一个模式)。

sed地址需要GNU 0(并且能够b在同一表达式中的命令之后包含其他命令,尽管这可以通过使用两个表达式在其他实现中轻松解决-e

awk

awk '$0 != "AAA" || !n++'

(或者对于正则表达式模式awk '!/^AAA$/ || !n++':)

的简写:

awk '! (&0 == "AAA" && count > 0) {print; count++}'

答案2

Stéphane Chazelas 的awk解决方案是美丽的:

awk '!/AAA/ || !n++' file.in

这可以概括为

awk '$0 !~ pattern || !n++' pattern="$pattern" file.in

$pattern对于包含一些正则表达式的给定 shell 变量。

如果$pattern包含反斜杠,则需要对其进行转义(\\),或者您可以使用

P="$pattern" awk '$0 !~ ENVIRON["P"] || !n++' file.in

答案3

每次遇到该行时只需交换缓冲区,如果模式空间包含相同的行,则将其删除,否则从保留缓冲区中检索该行:

sed -e '/^AAA$/{x;//d;g' -e'}' infile

或者

sed '/^AAA$/{
x
//d
g
}' infile

相关内容