我有两个文件:s2.txt
14 3KC12828ACBA
43 8DG59242BAAD
25 8DG60566AAAF
6 8DG60912AAAF
和pbas.txt:
3AG33662AAAC
3KC12828ACBA
8DG59242BAAD
8DG60349AAAC
8DG60565AAAG
8DG60566AAAF
8DG60568AAAC
8DG60912AAAF
8DG62635AAAC
在 UNIX 上使用 bash 我想加入文件以获得一个如下文件:
3AG33662AAAC
3KC12828ACBA 14
8DG59242BAAD 43
8DG60349AAAC
8DG60565AAAG
8DG60566AAAF 25
8DG60568AAAC
8DG60912AAAF 6
8DG62635AAAC
怎样才能做到呢?
答案1
这就是join
:
join -2 2 -a 1 pbas.txt s2.txt
选项说:
-2 2
:第二个文件使用第二列来存储密钥-a 1
:输出文件 1 中的所有行,即使文件 2 中没有匹配项。
答案2
AWK
在 awk 中实现这一点相当容易:
$ awk 'NR==FNR{a[$2]=$1; next}{print $1,a[$1]}' file1.txt file2.txt
3AG33662AAAC
3KC12828ACBA 14
8DG59242BAAD 43
8DG60349AAAC
8DG60565AAAG
8DG60566AAAF 25
8DG60568AAAC
8DG60912AAAF 6
8DG62635AAAC
没有什么特别的事情 - 这种技术经常被那些awk
经常使用的人使用,特别是在处理多个文件时,它基于将信息从第一个文件加载到数组中的想法。
其工作原理很简单。首先使用NR==FNR
(当前处理的行号和当前文件中的行号之间的比较)我们将所有内容file1.txt
(在OP的示例中s2.txt
)读取到关联值数组中。 next
关键字允许我们在第一个文件中跳过下一个代码块。一旦我们退出第一个文件,下一个代码块将被执行,始终打印字段 1,并打印数组中的相应项(如果存在)。
珀尔
使用与 awk 类似的想法,我们可以在 Perl 中实现类似的结果,如下所示:
perl -lane 'if($F[1]){$hash{$F[1]}=$F[0]}else{print "$_ $hash{$_}"}' file1.txt file2.txt