Python:读取文本文件的一部分

时间:2009-06-08 13:44:33

标签: python

全部

我是python和编程的新手。我需要读取一个大文本文件的块,格式如下所示:

<word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head-"7" relation="ADV"/>

我需要formlemmapostag信息。例如对于上面我需要hibernishibernus1n-p---nb-

如何告诉python在到达表单之前读取,向前读取直到它到达引号"然后读取引号"hibernis"之间的信息?真的很挣扎。

到目前为止,我的尝试是删除标点符号,拆分句子,然后从列表中提取我需要的信息。虽然让python迭代整个文件有困难但我只能让这个工作为1行。我的代码如下:

f=open('blank.txt','r')
quotes=f.read()
noquotes=quotes.replace('"','')
f.close()

rf=open('blank.txt','w')
rf.write(noquotes)
rf.close()   

f=open('blank.txt','r')
finished = False
postag=[]
while not finished:
   line=f.readline()
   words=line.split()
   postag.append(words[4])
   postag.append(words[6])
   postag.append(words[8])              
   finished=True

非常感谢任何反馈/批评

感谢

9 个答案:

答案 0 :(得分:5)

如果是XML,请使用ElementTree来解析它:

from xml.etree import ElementTree

line = '<word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head="7" relation="ADV"/>'

element = ElementTree.fromstring(line)

对于每个XML元素,您可以轻松提取名称和所有属性:

>>> element.tag
'word'
>>> element.attrib
{'head': '7', 'form': 'hibernis', 'postag': 'n-p---nb-', 'lemma': 'hibernus1', 'relation': 'ADV', 'id': '8'}

因此,如果您的文档包含大量word XML元素,那么这样的内容将从每个元素中提取您想要的信息:

from xml.etree import ElementTree

XML = '''
<words>
    <word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head="7" relation="ADV"/>
</words>'''

root = ElementTree.fromstring(XML)

for element in root.findall('word'):
    form = element.attrib['form']
    lemma = element.attrib['lemma']
    postag = element.attrib['postag']

    print form, lemma, postag

如果您只有文件名,请使用parse()代替fromstring()

答案 1 :(得分:2)

我建议使用正则表达式模块:re

沿着这些方向可能会有什么?

#!/usr/bin/python
import re

if __name__ == '__main__':
    data = open('x').read()
    RE = re.compile('.*form="(.*)" lemma="(.*)" postag="(.*?)"', re.M)
    matches = RE.findall(data)
    for m in matches:
        print m

这假设<word ...>行分别在一行上,并且每个部分都按照确切的顺序排列,并且您不需要处理完整的xml解析。

答案 2 :(得分:1)

您的文件是否是正确的XML?如果是这样,请尝试使用SAX解析器:

import xml.sax
class Handler (xml.sax.ContentHandler):
   def startElement (self, tag, attrs):
       if tag == 'word':
           print 'form=', attrs['form']
           print 'lemma=',attrs['lemma']
           print 'postag=',attrs['postag']

ch = Handler ()
f = open ('myfile')
xml.sax.parse (f, ch)

(这很粗糙......可能不完全正确)。

答案 3 :(得分:1)

除了通常的RegEx答案之外,由于这似乎是一种XML形式,您可以尝试类似BeautifulSoup(http://www.crummy.com/software/BeautifulSoup/

它非常易于使用,并且可以在HTML / XML等内容中找到标签/属性,即使它们没有“格式良好”。也许值得一瞧。

答案 4 :(得分:0)

手工解析xml通常是    错了。首先,你的代码    如果有逃脱将会破裂    引用任何属性。    从xml获取属性    解析器可能更清晰,更少    容易出错。

如果您的行与格式不匹配,这样的方法也会在解析整个文件时遇到问题。您可以通过创建一个parseline方法(类似

)来处理这个问题
def parse (line):
      try: 
          return parsed values here
        except: 

您还可以使用过滤器和地图功能简化此操作:

lines = filter( lambda line: parseable(line), f.readlines())
values = map (parse, lines)

答案 5 :(得分:0)

只是为了突出你的问题:

finished = False
counter = 0
while not finished:
   counter += 1
   finished=True
print counter

答案 6 :(得分:0)

使用正则表达式,这是要点(你可以做file.readline()部分):

import re
line = '<word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head-"7" relation="ADV"/>'
r = re.compile( 'form="([^"]*)".*lemma="([^"]*)".*postag="([^"]*)"' )
match = r.search( line )
print match.groups()

>>> 
('hibernis', 'hibernus1', 'n-p---nb-')
>>> 

答案 7 :(得分:0)

首先,不要花很多时间重写文件。这通常是浪费时间。清理和解析标签的过程非常快,以至于您始终可以非常高兴地使用源文件。

source= open( "blank.txt", "r" )
for line in source:
    # line has a tag-line structure
    # <word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head-"7" relation="ADV"/>
    # Assumption -- no spaces in the quoted strings.
    parts = line.split()
    # parts is [ '<word', 'id="8"', 'form="hibernis"', ... ]
    assert parts[0] == "<word"
    nameValueList = [ part.partition('=') for part in parts[1:] ]
    # nameValueList is [ ('id','=','"8"'), ('form','=','"hibernis"'), ... ]
    attrs = dict( (n,eval(v)) for n, _, v in nameValueList )
    # attrs is { 'id':'8', 'form':'hibernis', ... }
    print attrs['form'], attrs['lemma'], attrs['posttag']

答案 8 :(得分:0)

哇,你们快啊:) 如果你想要列表的所有属性(并且知道了顺序),那么你可以使用这样的东西:

import re
print re.findall('"(.+?)"',INPUT)

INPUT是一行:

<word id="8" form="hibernis" lemma="hibernus1" postag="n-p---nb-" head="7" relation="ADV"/>

,打印清单是:

['8', 'hibernis', 'hibernus1', 'n-p---nb-', '7', 'ADV']