Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/solr/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
AWK:在不同列上使用特殊格式从一个文件到另一个文件的部分匹配_Awk - Fatal编程技术网

AWK:在不同列上使用特殊格式从一个文件到另一个文件的部分匹配

AWK:在不同列上使用特殊格式从一个文件到另一个文件的部分匹配,awk,Awk,我的TSVfile1(它有更多的额外列,但为了简单起见减少了),其中感兴趣的列是CHROM和POS: CHROM POS REF ALT QUAL MoreColumns chr11 8823729 G C 605.77 ... chr1 16619 C T 95.77 ... chr1 16949 A C 559.77 ...

我的TSV
file1
(它有更多的额外列,但为了简单起见减少了),其中感兴趣的列是
CHROM
POS

CHROM   POS         REF     ALT     QUAL    MoreColumns
chr11   8823729     G       C       605.77  ...
chr1    16619       C       T       95.77   ...
chr1    16949       A       C       559.77  ...
chr1    17005       A       G       172.77  ...
chr1    17020       G       A       345.77  ...
chr12   8822661     G       A       880.77  ...
chr1    17697       G       C       412.77  ...
chr14   8837474     T       C       411.77  ...
chr1    129285      G       A       2509.77 ...
我的TSV
file2
示例,其中感兴趣的列是
Extra_information
,格式如下:

Column1 ... Column9     Extra_information                                                       Column11
data    ... longline    hg38:Chr12:8822661, hg19:Chr12:8975257, COM:morewords, dbSNP:link       No
data2   ... longline2   hg38:Chr11:8823729, hg19:chr12:8976325, COM:morewords2, dbSNP:link2     No
data3   ... longline3   hg38:chr12:8823762, hg19:Chr12:8976358, COM:morewords3                  Yes
data4   ... longline4   hg38:chr12:8835642, hg19:Chr12:8988238, dbSNP:link3                     No
data5   ... longline5   hg38:Chr14:8837474, hg19:chr12:8990070, dbSNP:link4                     Yes
data6   ... longline6   hg19:Chr12:8990937, COM:morewords4, dbSNP:link5                         No
data7   ... longline7   hg38:chr12:8839209, PC:someinfo                                         No
我的问题是:

我想从
file1
执行
hg38:CHROM:POS
file2
Extra\u信息的部分匹配,并打印
file1
+
“\t”1的行,如果部分匹配为真,则打印
file1的其他行
Chr
也可以是
file2
中的
Chr
附加信息中的

我想要的第一个输出

CHROM   POS         REF     ALT     QUAL    MoreColumns     Match
chr11   8823729     G       C       605.77  ...             1
chr1    16619       C       T       95.77   ...             0
chr1    16949       A       C       559.77  ...             0
chr1    17005       A       G       172.77  ...             0
chr1    17020       G       A       345.77  ...             0
chr12   8822661     G       A       880.77  ...             1
chr1    17697       G       C       412.77  ...             0
chr14   8837474     T       C       411.77  ...             1
chr1    129285      G       A       2509.77 ...             0
我的首选第二输出

CHROM   POS         REF     ALT     QUAL    MoreColumns     Column1 ... Column9     Extra_information                                                       Column11
chr11   8823729     G       C       605.77  ...             data2   ... longline2   hg38:Chr11:8823729, hg19:chr12:8976325, COM:morewords2, dbSNP:link2     No
chr1    16619       C       T       95.77   ...             -       ... -               -                                                                   -
chr1    16949       A       C       559.77  ...             -       ... -               -                                                                   -
chr1    17005       A       G       172.77  ...             -       ... -               -                                                                   -
chr1    17020       G       A       345.77  ...             -       ... -               -                                                                   -
chr12   8822661     G       A       880.77  ...             data    ... longline    hg38:Chr12:8822661, hg19:Chr12:8975257, COM:morewords, dbSNP:link       No
chr1    17697       G       C       412.77  ...             -       ... -               -                                                                   -
chr14   8837474     T       C       411.77  ...             data5   ... longline5   hg38:Chr14:8837474, hg19:chr12:8990070, dbSNP:link4                     Yes
chr1    129285      G       A       2509.77 ...             -       ... -               -                                                                   -
我试过:

awk-F$'\t''NR==FNR
{a=((“hg38:“文件1[$1]”):“文件1[$2]);a=$NF;next}
{如果($10~$NF){
打印文件1[$0]“\t1”
}否则{
打印文件1[$0]“\t0”
}
}'文件1文件2
如何使用
awk
实现所需的输出(最好是第二个)?(或者如果您可以提出任何其他bash解决方案)

先谢谢你

注意:我从
file1
中有~70k行,用于执行与包含~160k行的
file2
的部分匹配

编辑: 根据@Hai Vu对完整线路的要求:

File1

文件2


这里有一种解决方法。我创建了一个AWK脚本,并将其命名为hg38.AWK。要调用它:

awk -f hg38.awk file2 file1
请注意,我先扫描文件2,再扫描文件1。以下是脚本:

# In file2 where we found hg38
# We transform "hg38:Chr11:8823729," to "chr11:8823729"
# And use that as a key in the array `found`
NR == FNR && $4 ~ /^hg38:/ {
    extra = $4
    sub(/hg38:/, "", extra)
    sub(/Chr/, "chr", extra)
    sub(/,$/, "", extra)
    found[extra] = 1
}

# First line of file1
# Print the existing headers and an additional column
NR != FNR && FNR == 1 {
    print $0 "\tMatch"
    next
}

# Subsequent lines of file1
NR != FNR {
    printf $0
    key = $1 ":" $2
    if (key in found) {
        print "\t1"
    } else {
        print "\t0"
    }
}
解释
  • 在脚本中,我首先扫描file2(请参见命令行)。为了区分这两个文件,我研究了
    NR
    FNR
    变量之间的关系。如果它们相同,我将扫描命令行上的第一个文件(因此是file2)。如果它们不同,我正在处理文件1
  • 对于第一个和第二个代码块,我希望注释足够
  • 在最后一个块中,我从字段中构造了键,例如“chr11:8823729”,并检查该键是否在数组
    中找到
    并相应地输出
使现代化 在这里,我修改了脚本以输出第二个所需的输出。这些更改包括存储file2的整行和构造一个空行

NR == FNR && FNR == 1 {
    headers = $0
    empty_row = ""
    for (i = 0; i < NF; i++) {
        empty_row = "\t-" empty_row
    }
    next
}

# In file2 where we found hg38
# We transform "hg38:Chr11:8823729," to "chr11:8823729"
# And use that as a key in the array `found`
NR == FNR && $4 ~ /^hg38:/ {
    extra = $4
    sub(/hg38:/, "", extra)
    sub(/Chr/, "chr", extra)
    sub(/,$/, "", extra)
    found[extra] = $0
}

# First line of file1
# Print the existing headers and an additional column
NR != FNR && FNR == 1 {
    print $0 "\t" headers
    next
}

# Subsequent lines of file1
NR != FNR {
    printf $0
    key = $1 ":" $2
    if (key in found) {
        print "\t" found[key]
    } else {
        print empty_row
    }
}
NR==FNR&&FNR==1{
页眉=$0
空_行=“”
对于(i=0;i
更新2 根据谷歌的最新数据,我发现file2.tsv字段10比我想象的要复杂。有了这一点,我就能够制定出解决方案的第3版:

# Works with TSV  (tab-separated values) file
BEGIN {
    FS = "\t"
}

# In file2.tsv, save the headers and create a row of empty data (just dashes)
NR == FNR && FNR == 1 {
    headers = $0
    empty_row = ""
    for (i = 0; i < NF; i++) {
        empty_row = "\t-" empty_row
    }
    next
}

# In file2.tsv where we found hg38
# We transform "hg38:Chr11:8823729," to "chr11:8823729"
# And use that as a key in the array `found`
NR == FNR && $10 ~ /^hg38:/ {
    extra = $10
    sub(/hg38:/, "", extra)
    sub(/Chr/, "chr", extra)
    sub(/,.*$/, "", extra)
    found[extra] = $0
}

# First line of file1
# Print the existing headers and additional columns
NR != FNR && FNR == 1 {
    print $0 "\t" headers
    next
}

# Subsequent lines of file1
NR != FNR {
    printf $0
    key = $1 ":" $2
    if (key in found) {
        print "\t" found[key]
    } else {
        print empty_row
    }
}
#使用TSV(制表符分隔值)文件
开始{
FS=“\t”
}
#在file2.tsv中,保存标题并创建一行空数据(仅短划线)
NR==FNR&&FNR==1{
页眉=$0
空_行=“”
对于(i=0;i
感谢您提出的答案和解释!对于第一个块,我将
$4
更改为
$10
,因为我的
额外信息
位于第10列。我尝试了您的脚本,但它仍然打印了匹配的
键的
-
。提供file1和file2的完整行如何,只需选择几行并用类似“XXX”的其他内容替换敏感数据您可以用tabs@Zen,文件中的某些单元格有空格。这意味着将空格转换为制表符将导致数据不对齐。你能把你的文件转换成TSV并上传到某个地方吗?或者将它们转换为逗号分隔值(CSV)文件?这很好。继续实施你的改变。祝你好运。在这种情况下,最好使用Unix提供的工具。例如,在本例中,Unix提供了一个执行所需连接的join命令。使用awk预处理器将文件转换为join所需的格式,运行join,然后使用awk后处理器生成最终输出。两个awk程序将很简单;复杂性在于Unix为您提供的连接。