删除相似的行?

Deleting similar lines?

我一直在使用它来删除第一个文件中第二个文件中的行(差异)。

awk 'FNR==NR{a[[=10=]]++}FNR!=NR && !a[[=10=]]{print}' file2.txt file1.txt >output.txt

这对于完全相同的行非常有效,而且对于具有数百万行的文件也能快速处理。 现在,我偶然发现我的行与第一个文件中的行相似,但不完全相同,有些行在开头附加了 8-9 个字符,但直到行尾都是相同的,像这样:

文件 1

8952aa182685763d30758c730de536a9907f96e7
5e46468f50df8e410b0372dc8a550c0cec33d8bc
11111111-954f94fa00c220c40a49b37816c9146
5dd0a2058734e2c3e039f3a814fc86789474c65e
2222222-s54b2c1d6176b0aae91d85545670aa7a

文件 2

5e46468f50df8e410b0372dc8a550c0cec33d8bc
954f94fa00c220c40a49b37816c9146
s54b2c1d6176b0aae91d85545670aa7a

想要的结果:

8952aa182685763d30758c730de536a9907f96e7
5dd0a2058734e2c3e039f3a814fc86789474c65e

我试图找到解决方案,但到目前为止我还没有找到,如果您有已经解决的解决方案,请分享一个 link,在此先感谢。

file2 中不部分匹配的情况下查找 file1 中的行的最简单方法是:

grep -v -f file2 file1

file2 中列出的那些行与 file1 中的行进行反向匹配,结果是:

8952aa182685763d30758c730de536a9907f96e7
5dd0a2058734e2c3e039f3a814fc86789474c65e

我相信你真正想要的是:

$ awk -F'-' '(FNR==NR){a[$NF]; next}!($NF in a)' file2 file1

这会将每一行拆分为由 - 分隔的字段。因此对于 file1,$NF 值由

给出
8952aa182685763d30758c730de536a9907f96e7 -> 8952aa182685763d30758c730de536a9907f96e7
5e46468f50df8e410b0372dc8a550c0cec33d8bc -> 5e46468f50df8e410b0372dc8a550c0cec33d8bc
11111111-954f94fa00c220c40a49b37816c9146 -> 954f94fa00c220c40a49b37816c9146
5dd0a2058734e2c3e039f3a814fc86789474c65e -> 5dd0a2058734e2c3e039f3a814fc86789474c65e
2222222-s54b2c1d6176b0aae91d85545670aa7a -> s54b2c1d6176b0aae91d85545670aa7a

这正是您要从 file2 匹配的字符串,它也被 $NF 引用,因为它包含一个字段。但是,如果行中自然有更多的连字符,这可能会有问题。

这个 可能 比 grep 解决方案更好,因为 grep 解决方案可能会消除误报。想象一下 file1 中的行看起来像:

xxs54b2c1d6176b0aae91d85545670aa7axxxxxx
yyys54b2c1d6176b0aae91d85545670aa7ayyyyy
zzzzs54b2c1d6176b0aae91d85545670aa7azzzz

所有这些都将被删除。在上述情况下,情况并非如此。

您也可以通过陈述

以不同方式解决问题

Don't show the lines of file1 where the lines of file2 match the end of the corresponding line in line1.

这可以通过以下方式用awk解决:

$ awk '(FNR==NR){a[[=13=]]; next}
       {for(str in a) if (index([=13=],str)+length(str)-1==length([=13=])) print }' file2 file1

我们本可以使用 match 而不是 index,但是 match 将匹配 ERE 模式,如果 str 包含任何特殊的 ERE 模式,它将无法达到目的.