当第二个文件列包含逗号时,使用 awk 将一个文件的列与另一个文件的列匹配
Match column of one file to column of another using awk when second file column contains commas
我有两个文件 - 一个是包含基因变体的大文件,多列由制表符分隔。包含基因名称的列可能包含单个名称,或以逗号分隔的多个名称(示例中的基因名称是 SAMD11 和 NOC2L):
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 881918 881918 G A rs35471880 NOC2L exonic ENSG00000188976 nonsynonymous SNV
1 888659 888659 T C rs3748597 NOC2L exonic ENSG00000188976 nonsynonymous SNV
第二个文件是基因名称的单列列表,例如:
EVC2
SAMD11
COMT
我想将第二个文件中的基因名称与第一个文件中的基因名称相匹配。我目前正在使用 awk:
awk -F $'\t' 'BEGIN { while(getline <"secondfile.txt") gene[[=12=]]=1; } gene[]' firstfile.txt > newfile.txt
但是,这只会打印完全匹配的内容,因此不会打印带有 NOC2L,SAMD11 的行。从上面的示例中,预期输出将是第一个文件的前四行:
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
我希望它仍然进行精确匹配,因为一些基因名称可能相似 - 例如,可能有一个名为 SAMD1 的基因,如果我对其进行模糊匹配,那么我会得到 SAMD1、SAMD11 和很快。所以我需要一些可以完全匹配但忽略基因名称列中的逗号,或将其视为字段分隔符或类似内容的东西。
提前致谢。
$ cat tst.awk
NR==FNR { genes[[=10=]]; next }
{
split(,a,/,/)
for (i in a) {
if (a[i] in genes) {
print
next
}
}
}
$ awk -f tst.awk secondfile.txt firstfile.txt
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
这也行得通:
$ cat tst.awk
NR==FNR { genes[[=11=]]; next }
{
for (gene in genes) {
if ( ~ "(^|,)"gene"(,|$)") {
print
next
}
}
}
我有两个文件 - 一个是包含基因变体的大文件,多列由制表符分隔。包含基因名称的列可能包含单个名称,或以逗号分隔的多个名称(示例中的基因名称是 SAMD11 和 NOC2L):
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 881918 881918 G A rs35471880 NOC2L exonic ENSG00000188976 nonsynonymous SNV
1 888659 888659 T C rs3748597 NOC2L exonic ENSG00000188976 nonsynonymous SNV
第二个文件是基因名称的单列列表,例如:
EVC2
SAMD11
COMT
我想将第二个文件中的基因名称与第一个文件中的基因名称相匹配。我目前正在使用 awk:
awk -F $'\t' 'BEGIN { while(getline <"secondfile.txt") gene[[=12=]]=1; } gene[]' firstfile.txt > newfile.txt
但是,这只会打印完全匹配的内容,因此不会打印带有 NOC2L,SAMD11 的行。从上面的示例中,预期输出将是第一个文件的前四行:
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
我希望它仍然进行精确匹配,因为一些基因名称可能相似 - 例如,可能有一个名为 SAMD1 的基因,如果我对其进行模糊匹配,那么我会得到 SAMD1、SAMD11 和很快。所以我需要一些可以完全匹配但忽略基因名称列中的逗号,或将其视为字段分隔符或类似内容的东西。
提前致谢。
$ cat tst.awk
NR==FNR { genes[[=10=]]; next }
{
split(,a,/,/)
for (i in a) {
if (a[i] in genes) {
print
next
}
}
}
$ awk -f tst.awk secondfile.txt firstfile.txt
1 874816 874816 - T rs200996316 SAMD11 exonic ENSG00000187634 frameshift insertion
1 878331 878331 C T rs148327885 SAMD11 exonic ENSG00000187634 nonsynonymous SNV
1 879676 879676 G A rs6605067 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
1 879687 879687 T C rs2839 NOC2L,SAMD11 UTR3 ENSG00000187634,ENSG00000188976
这也行得通:
$ cat tst.awk
NR==FNR { genes[[=11=]]; next }
{
for (gene in genes) {
if ( ~ "(^|,)"gene"(,|$)") {
print
next
}
}
}