Linux删除重复行 排序和不排序的做法

本文介绍了一种在Linux环境下,利用awk命令去除文件中重复行同时保持原有行顺序的方法。通过一个具体的例子展示了如何使用awk实现这一功能,并解释了其工作原理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本文部分翻译自这里,来自 Jadu Saikia 的博客,这个博客上有很多非常有用的小技巧,有空可以多看看。

通常如果我们想获取一个文件里不重复的行的时候,我们可以直接通过 sort -u 命令,先把文件排序,然后去掉连续的重复行就行。

可是,如果我们去掉重复行之后,还想保留文件原有的顺序,该怎么办呢?虽然 Linux 下有个看上去似乎很有用的命令叫uniq,但事实上 uniq 命令仅仅只对连续的重复行有效。譬如我们有这样一个文件:

$ cat file3
AAAA
FFFF
BBBB
BBBB
CCCC
AAAA
FFFF
DDDD

如果不排序,直接使用 uniq 命令是没有用的:

$ uniq file3
AAAA
FFFF
BBBB
CCCC
AAAA
FFFF
DDDD

使用 sort -u 的话,我们就丢失了文件原有的行的顺序了:

$ sort -u file3
AAAA
BBBB
CCCC
DDDD
FFFF

sort 和 uniq 一起用,和 sort -u 效果是一样的:

$ sort file3 | uniq
AAAA
BBBB
CCCC
DDDD
FFFF

一个终极的解决方案是使用 awk:

$ awk ' !x[$0]++' file3
AAAA
FFFF
BBBB
CCCC
DDDD

简要解释一下,awk 的基本执行流程是,对文件的每一行,做一个指定的逻辑判断,如果逻辑判断成立,则执行指定的命令;如果逻辑判断不成立,则直接跳过这一行。

我们这里写的 awk 命令是 !x[$0]++,意思是,首先创建一个 map 叫 x,然后用当前行的全文 $0 作为 map 的 key,到 map 中查找相应的 value,如果没找到,则整个表达式的值为真,可以执行之后的语句;如果找到了,则表达式的值为假,跳过这一行。由于表达式之后有 ++,因此如果某个 key 找不到对应的 value,该 ++ 操作会先把对应的 value 设成 0,然后再自增成 1,这样下次再遇到重复的行的时候,对应的 key 就能找到一个非 0 的 value 了。

我们前面说过,awk 的流程是先判断表达式,表达式为真的时候就执行语句,可是我们前面写的这个 awk 命令里只有表达式,没有语句,那我们执行什么呢?原来,当语句被省略的时候,awk 就执行默认的语句,即打印整个完整的当前行。就这样,我们通过这个非常简短的 awk 命令实现了去除重复行并保留原有文件顺序的功能。

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值