使用“拆分行”;来自python中的内嵌

使用“拆分行”;来自python中的内嵌,python,split,Python,Split,我有一系列输入文件,例如: chr1 hg19_refFlat exon 44160380 44160565 0.000000 + . gene_id "KDM4A"; transcript_id "KDM4A"; chr1 hg19_refFlat exon 19563636 19563732 0.000000 - . gene_id "EMC1"; transcript_id "EMC1"; chr1

我有一系列输入文件,例如:

chr1    hg19_refFlat    exon    44160380    44160565    0.000000    +   .   gene_id "KDM4A"; transcript_id "KDM4A";
chr1    hg19_refFlat    exon    19563636    19563732    0.000000    -   .   gene_id "EMC1"; transcript_id "EMC1";
chr1    hg19_refFlat    exon    52870219    52870551    0.000000    +   .   gene_id "PRPF38A"; transcript_id "PRPF38A";
chr1    hg19_refFlat    exon    53373540    53373626    0.000000    -   .   gene_id "ECHDC2"; transcript_id "ECHDC2_dup2";
chr1    hg19_refFlat    exon    11839859    11840067    0.000000    +   .   gene_id "C1orf167"; transcript_id "C1orf167";
chr1    hg19_refFlat    exon    29037032    29037154    0.000000    +   .   gene_id "GMEB1"; transcript_id "GMEB1";
chr1    hg19_refFlat    exon    103356007   103356060   0.000000    -   .   gene_id "COL11A1"; transcript_id "COL11A1";
在我的代码中,我试图从每行中捕获2个元素,第一个是数字,后面写着外显子,第二个是基因(数字和字母组合用“”括起来,例如“KDM4A”)。下面是我的代码:

    with open(infile,'r') as r:
        start = set([line.strip().split()[3] for line in r])
        genes = set([line.split('"')[1] for line in r])
        print len(start)
        print len(genes)
出于某种原因,start工作正常,但基因没有捕获任何东西。以下是输出:

 48050
 0
set(['44160380', '29037032', '103356007', '19563636', '53373540', '52870219', '11839859'])
set(['COL11A1', 'PRPF38A', 'KDM4A', 'C1orf167', 'EMC1', 'GMEB1', 'ECHDC2_dup2'])
我想这与基因名称周围的“”有关,但如果我在终端上输入它,它会正常工作:

>>> x = 'A b P "G" m'
>>> x
'A b P "G" m'
>>> x.split('"')[1]
'G'
>>> 

任何解决方案都将不胜感激,即使这是一种从每行捕获2项数据的完全不同的方式。谢谢,这是因为当您在此处循环一次时,您的文件对象已耗尽
start=set([line.strip().split()[3]用于r中的行])
再次尝试在此处循环
genes=set([line.split(“”)[1]用于r中的行]
在耗尽的文件对象上

解决方案:

with open(infile,'r') as r:
    start = set([line.strip().split()[3] for line in r])
    r.seek(0, 0)
    genes = set([line.split('"')[1] for line in r])
    print len(start)
    print len(genes)
您可以查找文件的开头(这是解决方案之一)

对代码的修改:

with open(infile,'r') as r:
    start = set([line.strip().split()[3] for line in r])
    r.seek(0, 0)
    genes = set([line.split('"')[1] for line in r])
    print len(start)
    print len(genes)
您可以使用正则表达式

with open(file) as f:
    start = []
    genes = []
    for line in f:
        st, gen = re.search(r'\bexon\s+(\d+)\b.*?\s+gene_id\s+"([^"]*)"', line).groups()
        start.append(st)
        genes.append(gen)
    print set(start)
    print set(genes)

您可以将所有行加载到一个列表中,然后对该列表中的每一项执行
拆分
(如果文件很长,则不确定效率有多高)

使用shlex(就像shell参数一样)可以中和多个空格和引号
不确定它是否更快,但安全而且还不错

import shlex
with open(infile, 'r') as f:
    for line in f:
        parts = shlex.split(line.replace(';', ''))
        print parts[3], parts[9]

它无法加载
基因的原因是您需要从一开始就重新开始读取文件。不过,以下方法应该可以工作:

import re

start = set()
genes = set()

with open('input.txt', 'r') as f_input:
    for line in f_input:
        s, g = re.match(r'(?:.*?\s+){3}(\d+).*"(\w+)"', line).groups()
        start.add(s)
        genes.add(g)

print start
print genes
为您提供输出:

 48050
 0
set(['44160380', '29037032', '103356007', '19563636', '53373540', '52870219', '11839859'])
set(['COL11A1', 'PRPF38A', 'KDM4A', 'C1orf167', 'EMC1', 'GMEB1', 'ECHDC2_dup2'])

现在你有两个问题!但是
start
genes
现在不是字符串而不是集合吗?看起来与OP最初的情况有很大不同。好吧,那么OP应该怎么做呢?谢谢,我以前没有遇到过seek方法,非常有用。我接受这个答案,因为它最短最简洁,解决了pr有一个短行的问题code@user3062260很高兴为您提供帮助我想到了这一点,但是文件太大了,我需要循环处理24个大小类似的文件,这样会花费很多时间。我以前没有遇到过shlex,它似乎可以很好地解决问题。不过,重置循环似乎是最简单的解决方案。