AWK 比较两个单独文件中的两列

AWK compare two columns in two seperate files

我想比较两个文件并执行如下操作:如果第一个文件中的第 5 列等于第二个文件中的第 5 列,我想打印第一个文件中的整行。那可能吗?我搜索了这个问题,但找不到解决方案:(

文件由制表符分隔,我试过这样的操作:

zcat file1.txt.gz file2.txt.gz | awk -F'\t' 'NR==FNR{a[];next} in a {print [=10=]}'

有没有人试过做类似的事情? :)

在此先感谢您的帮助!

您的脚本没问题,但您需要将每个文件单独提供给 awk 并以相反的顺序提供。

$ cat file1.txt
a b c d 100
x y z w 200
p q r s 300
1 2 3 4 400

$ cat file2.txt
. . . . 200
. . . . 400

$ awk 'NR==FNR{a[];next}  in a {print [=10=]}' file2.txt file1.txt
x y z w 200
1 2 3 4 400

编辑

正如评论中所指出的,上面的通用解决方案可以改进并适应 OP 从压缩的制表符分隔文件开始的情况:

$ awk -F'\t' 'NR==FNR{a[];next}  in a' <(zcat file2.txt) <(zcat file1.txt)
x y z w 200
1 2 3 4 400

解释:

NR是当前正在处理的记录的编号,FNR是编号 当前记录 在其文件 中。因此 NR == FNR 只是 当 awk 正在处理给它的第一个文件时为真(在我们的例子中是 file2.txt)。

a[] 将第 5 列的值作为索引添加到数组 a。 awk 中的数组是关联数组,但通常您并不关心关联一个值,而只想制作一个漂亮的东西集合。这是一个 收集我们在第 5 列中看到的所有值的简洁方法 第一个文件。接下来的 next 语句表示立即获取下一个 可用记录,无需查看 awk 程序中的任何语句。

总结以上内容,这一行表示“如果您正在阅读第一个文件 (file2.txt), 将第 5 列的值保存在名为 a 的数组中,然后继续记录没有 继续 awk 程序的其余部分。"

NR == FNR { a[]; next }

希望上面的内容很清楚,我们唯一能通过第一行的方法 awk 程序是如果我们正在读取第二个文件(file1.txt 在我们的例子中)。

in a 如果第 5 列的值作为索引出现在 a 数组。换句话说,对于 file1.txt 中的第 5 个记录 我们在 file2.txt.

的第 5 列中看到的列

在 awk 中,当模式部分计算为真时,伴随的动作是 调用。当没有给出动作时,如下所示,触发默认动作 相反,这是简单地打印当前记录。因此,只要说 in a,我们告诉 awk 打印第 5 个 file1.txt 中的所有记录 列也出现在 file2.txt 中,这当然是给定的要求。

 in a