我有三个文件格式如下:
$ cat a.bed
chr1 6 6 aa
chr1 8 8 bb
chr2 22 22 aa
chr3 24 24 bb
$ cat b.bed
chr1 12 12 cc
chr1 6 6 dd
chr5 14 14 cc
$ cat c.bed
chr1 8 8 ss
chr4 11 11 dd
chr1 6 6 aa
我想使用前两列比较这些文件并打印每行的信息,无论它是存在于一个文件还是多个文件中,如:
chr1 6 6 aa 3 a.bed,b.bed,c.bed
chr1 8 8 bb 2 a.bed,c.bed
chr2 22 22 aa 1 a.bed
chr3 24 24 bb 1 a.bed
chr1 12 12 cc 1 b.bed
chr5 14 14 cc 1 b.bed
chr4 11 11 dd 1 c.bed
其中第5列给出了它所存在的文件数,第6列给出了文件的名称。
答案 0 :(得分:0)
尝试这四行gawk(似乎没有在awk中工作):
gawk '{print $0, FILENAME}' a.bed > abc.bed
gawk '{print $0, FILENAME}' b.bed >> abc.bed
gawk '{print $0, FILENAME}' c.bed >> abc.bed
gawk '{f = $5;k=$1 " " $2 " " $3 " " $4;if(k in a){a[k] = a[k] "," f}else{a[k] = f};c[k]++};END{for(k in a){print k, c[k], a[k]}}' abc.bed
单个char变量简洁: f - 文件名, k - 键,即数据, a - 一系列键, c - 一系列密钥计数。
呃,如果我正确阅读,你的输入和输出数据样本不匹配,例如只有2' chr1 6 6 aa'不是3。
答案 1 :(得分:0)
awk
救援!
$ awk '{a[$1,$2]=(($1,$2) in a?a[$1,$2]",":$0 OFS)FILENAME}
END{for(k in a) print a[k]}' {a,b,c}.bed
结果虽然不会有相同的顺序。
<强>解释强>
x=c?a:b
是三元运算符,根据c的值将x设置为a或b(类似于if-then-else)。在这里,我们通过附加($1,$2)
(如果已经存在)或设置为当前行(再次附加FILENAME
)来为关键FILENAME
指定地图值。在END
块中,只需遍历此映射,然后打印值。