试图解析Python中的大型XML文件 - 内存错误

问题描述:

所以我是一个初学者的'刮刀',没有一整套的编程经验。试图解析Python中的大型XML文件 - 内存错误

我在Canopy环境中使用Python来提取一些下载的XML文件,并使用xml.dom解析器来执行此操作。我只是试图从第一个美国书目专利授权(这就是为什么我使用[0])只是为了看看我想要解析和存储整个数据集;而不是一次完成。从XML摘录如下:

<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE us-patent-grant SYSTEM "us-patent-grant-v42-2006-08-23.dtd" [ ]> 
<us-patent-grant lang="EN" dtd-version="v4.2 2006-08-23" file="USD0606726-20091229.XML" status="PRODUCTION" id="us-patent-grant" country="US" date-produced="20091214" date-publ="20091229"> 
<us-bibliographic-data-grant> 
<publication-reference> 
<document-id> 
<country>US</country> 
<doc-number>D0606726</doc-number> 
<kind>S1</kind> 
<date>20091229</date> 
</document-id> 
</publication-reference> 
<application-reference appl-type="design"> 
<document-id> 
<country>US</country> 
<doc-number>29299001</doc-number> 
<date>20071217</date> 

到目前为止我的代码看起来是这样的:

from xml.dom import minidom 

filename = "C:/Users/SMOLENSK/Documents/Inventor Research/xml_2009/ipg091229.xml" 

f = open(filename, 'r') 

doc = f.read() 

f.close() 

xmldata = '<root>' + doc + '</root>' 

data = minidom.parse(xmldata) 

US_Biblio = xmldata.getElementsByTagName("us-bibliographic-data-grant")[0] 

pat_num = US_Biblio.getElementsByTagName("doc-number")[0] 

dates = pat_num.getElementsByTagName("date") 

for date in dates: 
    print(date) 

现在我已经得到了内存错误某些消息后的代码完全运行,但它只是被能够运行一次,但不幸的是我无法记下发生了什么。由于数据的高负载(仅此文件为460万行),操作每次都会崩溃,我无法复制错误。

是否有任何人可以看到错误的代码?我的代码是在开始存储每个标记名称之前解析整个数据集,但是可能有一种方法仅解析一定数量?也许只是用第一组创建一个新的XML文件。

如果你想知道我用绕过的

ExpatError: junk after line xxx

我事先得到的问题。我知道我的编程技巧并不令人惊讶,所以希望我没有做出简单而令人厌恶的编程错误。

+0

要复制的整个文件中添加''标签。 'minidom.parse'将带有'file'对象。尝试使用'with'和'data = minidom.parse重复(f)' –

+0

嘿,迈克。很抱歉,尽管我确实理解我的'xmldata'是什么意思,但我不确定如何使用''重新使用''。你能帮助澄清一个偶然的例子吗? – HelloToEarth

+0

... [使用Python Iterparse For Large XML Files](https://*.com/q/7171140/2823755)...也许试试lxml。另外,minidomn有一个[unlink](https://docs.python.org/3/library/xml.dom.minidom.html#xml.dom.minidom.Node.unlink)方法,可以帮助释放不用的东西。每当你缩小搜索范围并做一个新的任务(例如'''''''''''''''',尝试删除前面的变量,(例如('''del data''') – wwii

尝试:

with open(filename, 'r') as f: 
    data = minidom.parse(f) 

如果你真的需要的标签,您可能需要更动了一下,说不定:

data = minidom.parse(itertools.chain('<root>', f, '</root>') 
+0

当我在'with'语句之外使用'itertools.chain'我得到了同样的_ExpatError:垃圾邮件在行xxx ..._之后,并在'with'语句中出现错误_AttributeError:'itertools.chain'对象没有属性'read'_ 我假设第一个又是由于数据本身重复的非确切的XML根元素,但是由于? – HelloToEarth

+0

,该属性错误发生了解析必须需要一个'file'对象(它有一个读取方法)。我们给它的链是一个迭代器返回字符串,但显然不是解析要的秒。 XML是否形成良好?如果不是,可以尝试'BeautifulSoup'包来解析它。 –

+0

看看这个(问题)[https://*.com/questions/45395811/parsing-xml-with-beautiful-soup]。这是你的问题的重复。 –