【问题标题】:Find pattern and print next column (two files)查找模式并打印下一列(两个文件)
【发布时间】:2014-03-09 06:54:00
【问题描述】:

我想在 File2 的 File1 的第 1 列中查找模式,然后在 File2 旁边打印 File1 的第二列:

File1(两列制表符分隔):

APBW    lung
APCA    non virulent
ABKM    lung
APBX    lung
KK020   -
APBZ    non virulent
AOSU    lung
APBY    non virulent
APBV    joint; lung; CNS
CP001321    virulent
APBT    virulent
APBU    non-virulent
APCB    moderadamente virulenta (nose)
CP005384    -

File2(两列制表符分隔):

HS372_00243 gi|219690483|gb|CP001321.1|
HS372_00436 gi|529264994|gb|APBX01000055.1|
HS372_00445 gi|529256455|gb|APBT01000061.1|
HS372_00544 gi|529259149|gb|APBV01000035.1|
HS372_00545 gi|529259149|gb|APBV01000035.1|
HS372_00546 gi|529259149|gb|APBV01000035.1|

所需的输出(三列制表符分隔):

HS372_00243 gi|219690483|gb|CP001321.1| virulent
HS372_00436 gi|529264994|gb|APBX01000055.1| lung
HS372_00445 gi|529256455|gb|APBT01000061.1| virulent
HS372_00544 gi|529259149|gb|APBV01000035.1| jointlungCNS
HS372_00545 gi|529259149|gb|APBV01000035.1| jointlungCNS
HS372_00546 gi|529259149|gb|APBV01000035.1| jointlungCNS

临时 bash 代码(不工作),但对其他语言开放:

while read vl; do grep "$vl" File2 ; done < File1

还尝试使用 awk(不工作,因为它似乎正在寻找完全匹配并且我在 File2 中的字符串被其他东西包围):

awk 'BEGIN { FS = OFS = "\t" } FNR==NR{a[$1]=$0;next}($1 in a){print a[$1],$2,$3}' File1 File2

谢谢,伯纳多

【问题讨论】:

  • 不清楚你从文件1到文件2使用的模式。有时是同一个,有时是前四个字母...
  • File1 中的模式长度不同
  • 我的意思是,给定您的示例文件 1,当在文件 2 中找到 APBX01000055 时不应写入任何内容,因为 APBX01000055 不在文件 1 中。
  • 好的,我明白了。问题是我想打印 'lung' 只需找到不完整的 'APBX' 字符串
  • 嗯,这不一致。如果我们得到这个,那么这意味着我们必须检查 4 个字符。但是CP001321 会发生什么?

标签: python perl bash awk bioinformatics


【解决方案1】:

这样的事情听起来像你想要的:

awk '
BEGIN { FS=OFS="\t" }
NR==FNR { map[$1] = $2; next }
{
    for (key in map)
        if ($0 ~ key)
            $0 = $0 OFS map[key]
    print
}
' file1 file2

【讨论】:

  • 不需要,它已经足够快了,如果我要加快速度,肯定不会有 break 语句。
  • 既然这个答案已经被接受,那么输出就不再是问题了。因为 OP 需要从 joint; lung; CNS 转换为 jointlungCNS
【解决方案2】:

希望对你有帮助

file2_contents = [i.strip() for i in open("file2.txt").readlines()]

with open("file1.txt") as file1:
    for each_line in file1.readlines():
        code=each_line.split('\t')[0].strip()
        part=each_line.split('\t')[1].strip()
        for each_file2_contents in file2_contents:
            if code in each_file2_contents:
                print  each_file2_contents+'\t'+part

【讨论】:

  • 那是 Perl 语言吗?我是新来的!
  • 你发布的python标签是python
【解决方案3】:

在 Perl 中:

use warnings;
use strict;
use Data::Dumper;

my $str1 = <<"EOS1";
APBW    lung
APCA    non virulent
ABKM    lung
APBX    lung
KK020   -
APBZ    non virulent
AOSU    lung
APBY    non virulent
APBV    joint; lung; CNS
CP001321    virulent
APBT    virulent
APBU    non-virulent
APCB    moderadamente virulenta (nose)
CP005384    -
EOS1

my $str2 = <<"EOS2";
HS372_00243 gi|219690483|gb|CP001321.1|
HS372_00436 gi|529264994|gb|APBX01000055.1|
HS372_00445 gi|529256455|gb|APBT01000061.1|
HS372_00544 gi|529259149|gb|APBV01000035.1|
HS372_00545 gi|529259149|gb|APBV01000035.1|
HS372_00546 gi|529259149|gb|APBV01000035.1|
EOS2

#HS372_00243 gi|219690483|gb|CP001321.1| virulent

my %data1;my %data2;
foreach my $line ( split(/\n+/,$str1) ){
    my @f = split(/\t/,$line);
    $data1{$f[0]} = $f[1];
}
my @data2 = split(/\n+/,$str2);
foreach my $line ( split(/\n+/,$str2) ){
    my @f  = split(/\t/,$line);
    my @sf = split(/\|/,$f[1]);

    $data2{$sf[3]} = $line;
}
#print Dumper(\%data2);
foreach my $s1 ( sort { length($b) <=> length($a) } keys %data1){
    foreach my $d2 (@data2){
        my @f  = split(/\t/,$d2);
        my @sf = split(/\|/,$f[1]);
        if ($sf[3] =~ m!^$s1!is){
            #warn "found $s1 in $d2\n";
            print "$d2\t$data1{$s1}\n";
        }
    }
}

output:
HS372_00243     gi|219690483|gb|CP001321.1|     virulent
HS372_00445     gi|529256455|gb|APBT01000061.1| virulent
HS372_00544     gi|529259149|gb|APBV01000035.1| joint; lung; CNS
HS372_00545     gi|529259149|gb|APBV01000035.1| joint; lung; CNS
HS372_00546     gi|529259149|gb|APBV01000035.1| joint; lung; CNS
HS372_00436     gi|529264994|gb|APBX01000055.1| lung

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-07-12
    • 2018-11-11
    • 1970-01-01
    • 2020-12-13
    • 1970-01-01
    • 2017-04-16
    • 2019-08-20
    相关资源
    最近更新 更多