使用lxml提取所有元素未提前知道的数据

时间:2010-11-17 04:41:25

标签: python parsing lxml sgml

我有一些大致标准化的sgml文件。但是,在打开文件并亲自阅读之前,标签中可能包含我不知道的数据。例如,文件具有地址,并且通常地址具有街道,城市,州,邮政编码和电话。地址的每个元素都用标记

表示
 <ADDRESS>
 <STREET>One Main Street
 <CITY>Gotham City
 <ZIP>99999 0123
 <PHONE>555-123-5467
 </ADDRESS>

但是,例如,我发现Country,STREET1,STREET2有标签。我有超过200K的文件要处理,我想知道是否有可能提取地址的所有元素而不必担心知道是否存在未知标记。

到目前为止,我所做的是

h=fromstring(my_data_in_a_string)
for each in h.cssselect('mail_address'):
    each.text_content()

但我得到的是有问题的,因为我无法确定一个元素的结束位置和下一个元素的开始

One Main StreetGotham City99999 0123555-123-5467

1 个答案:

答案 0 :(得分:2)

为了获得所有标签,我们通过这样的文件:

假设您的XML结构如下:

<ADDRESS>
 <STREET>One Main Street</STREET>
 <CITY>Gotham City</CITY>
 <ZIP>99999 0123</ZIP>
 <PHONE>555-123-5467</PHONE>
 </ADDRESS>

我们解析它:

>>> from lxml import etree
>>> f = etree.parse('foo.xml')  # path to XML file
>>> root = f.getroot() # get the root element
>>> for tags in root.iter(): # iter through the root element
...     print tags.tag       # print all the tags
... 
ADDRESS
STREET
CITY
ZIP
PHONE

现在假设你的XML也有额外的标签;你不知道的标签。由于我们正在迭代XML,上面的代码也将返回这些标记。

<ADDRESS>
         <STREET>One Main Street</STREET>
         <STREET1>One Second Street</STREET1>
        <CITY>Gotham City</CITY>
         <ZIP>99999 0123</ZIP>
         <PHONE>555-123-5467</PHONE>         
         <COUNTRY>USA</COUNTRY>    
</ADDRESS>

上面的代码返回:

ADDRESS
STREET
STREET1
CITY
ZIP
PHONE
COUNTRY

现在,如果我们想要获取标签的文本,那么过程是相同的。只需打印tag.text,如下所示:

>>> for tags in root.iter():
...     print tags.text
... 

One Main Street
One Second Street
Gotham City
99999 0123
555-123-5467
USA