提取数据XML - > Python中的DICT

时间:2017-06-23 07:19:29

标签: python xml python-2.7

我有这个包含和内部的xml文件。虽然我只得到第一个,但我无法遍历它们。这是xml结构和代码:

from lxml import objectify as xml_objectify
contents = open('/home/conacons/Documents/order.xml').read()
def xml_to_dict(xml_str):
""" Convert xml to dict, using lxml v3.4.2 xml processing library """
    def xml_to_dict_recursion(xml_object):
        dict_object = xml_object.__dict__
        if not dict_object:
            return xml_object
        for key, value in dict_object.items():
            dict_object[key] = xml_to_dict_recursion(value)
        return dict_object
    return xml_to_dict_recursion(xml_objectify.fromstring(xml_str))
xml_dict = xml_to_dict(contents)
#print xml_dict
for item,v in xml_dict['item']['items'].items():
    print item,v
<Order>
<item>
<customer></customer>
<status>no</status>
<amount_untaxed>7315.0</amount_untaxed>
<name>Test/001</name>
<confirmation_date>False</confirmation_date>
<order_id>8</order_id>
<items>
<item><list_price>16.5</list_price><description>False</description><weight>0.0</weight><default_code/><id>18</id><uom>Unit(s)</uom> <name>iPod</name></item><item><list_price>12.5</list_price><description>False</description><weight>0.0</weight><default_code>M-Wir</default_code><id>19</id><uom>Unit(s)</uom><name>Mouse, Wireless</name>     </item>

在运行此代码时,我只获得了一个ITEMS。如何使循环获取项目中的所有项目?谢谢 (输出): 项目{&#39; list_price&#39;:16.5,&#39;说明&#39;:&#39;错误&#39;,&#39;权重&#39;:0.0,&#39;默认_代码&#39; :你&#39;&#39; id&#39;:18,&#39;&#39;:&#39;单位&#39;,&#39; name&#39 ;:&#39; iPod&#39;}

1 个答案:

答案 0 :(得分:0)

您的方法存在问题。 XML对象未转换为dict,因为dict对象不能具有重复键。例如,如果您使用xml_object.__dict__xml_object子标记为item调用dict,则会返回item只有一个getchildren键。因此,您应该使用__init__方法而不是xml_object。但还有另一个问题。对于与您的示例中的items标记相对应的for child in xml_object.getchildren(): dict_object[child.tag] = xml_to_dict_recursion(child) ,下一个代码也无法正常工作:

child.tag

您理解的原因是在所有循环迭代中collections.defaultdict具有相同的值。

解决这些问题的一种可能方法是使用from collections import defaultdict from lxml import objectify def xml_to_dict(xml_str): def xml_to_dict_recursion(xml_object): dict_object = defaultdict(list) if not xml_object.__dict__: return xml_object for child in xml_object.getchildren(): dict_object[child.tag].append(xml_to_dict_recursion(child)) return dict_object return xml_to_dict_recursion(objectify.fromstring(xml_str)) if __name__ == "__main__": contents = open('input.xml').read() xml_dict = xml_to_dict(contents) for value in xml_dict['item'][0]['items'][0]['item']: print(dict(value)) 。代码可能如下所示:

{'uom': ['Unit(s)'], 'default_code': [''], 'description': ['False'], 'name': ['iPod'], 'weight': [0.0], 'list_price': [16.5], 'id': [18]}
{'uom': ['Unit(s)'], 'default_code': ['M-Wir'], 'description': ['False'], 'name': ['Mouse, Wireless'], 'weight': [0.0], 'list_price': [12.5], 'id': [19]}

在这种情况下,输出为:

lxml.objectify

但在我看来,这种方法并不那么方便,更简单的方法就是用tree = objectify.parse('input.xml') order = tree.getroot() order_items = order.getchildren() for order_item in order_items: print(order_item['amount_untaxed']) customer = order_item['customer'] print(customer['item']['city']) for item in order_item['items'].getchildren(): print(item['list_price']) 解析xml文档本身(参见docs)。例如:

Get-Module -ListAvailable -Name Azure -Refresh