遍历SAX
我有一个像这样的xml文件(这只是个例子):
<xml>
<page>
<lol>
</lol>
<lel>
</lel>
</page>
<page>
<lol>
</lol>
<lel>
</lel>
</page>
<page>
<lol>
</lol>
<lel>
</lel>
</page>
</xml>
我需要找到一种方法来做类似这样的事情:
#Sax code
for page in something:
parse(page)
我该如何用sax来实现这个呢?
这个xml文件有30GB的数据。
4 个回答
1
用xml.sax来做这件事,最有效和最符合Python风格的方法就是使用parser.feed()这个方法。
举个例子:
parser = xml.sax.make_parser()
parser.setContentHandler(YourContentHandler)
f = open('terribly_large.xml', 'r')
for line in f.xreadlines():
parser.feed(line)
这样做可以确保你在逐步读取文件的同时,也在逐步解析它。
这样占用的内存应该会很少。
1
不要使用SAX,建议使用ElementTree。
from xml.etree import cElementTree as ET
for event, elem in ET.iterparse("/path/to/your/file"):
if elem.tag == 'page':
# do your processing
elem.clear()
调用elem.clear()
是很重要的,否则你处理过的元素会一直保留在内存中,最终可能会占满你的所有内存。元素对象就像轻量级的DOM对象,所以使用起来比SAX简单多了。
如果每个page
元素已经大到无法放进你的内存,那你就得回到使用SAX了。不过从你的例子来看,似乎有很多小的page
元素,而不是几个大的。
0
你可以在一个线程里使用sax解析器。当它发现一个完整的页面时,就把这个页面放到一个队列里。在你的主线程中,循环遍历这个队列。