python中的XML vs Dictionary用于搜索和提取

时间:2015-03-31 00:02:50

标签: python xml dictionary

我有一个相当大的XML文件,我从monit的API中提取,使用Python中的以下代码。

file = urllib.request.urlopen(URL) #opening the XML URL
    data = file.read()
    file.close()
    list.append(parsedXML, xmltodict.parse(data)) #Parsing to dict the XML file created

我正在使用XMLtoDICT将XML转换为字典,因为我认为搜索和提取更容易。 XMLtoDICT创建了一个嵌套的有序字典,这很棒。但是,我没有看到一种简单的方法来搜索每个"""一个python dict并提取出一个整个节点。

有没有一种简单的方法可以在python中搜索和提取字典节点进行编辑?

例如,请查看下面的XML。一旦它出现在字典中,我需要提取以&#34; <service&#34;开头的每个节点。 (完整的XML文件中将有多个)并在该确切节点上运行测试,并且可能更改值 我还需要搜索字典中的所有值,找到一个值,然后获取该值的父节点名称并提取整个节点。这可能吗?

或者,我应该完全跳过字典并直接使用XML吗?如果是这样,是否有支持所有这些功能的XML python库?

以下是我要提取的XML数据示例:

    <monit>
    <server>
        <id>9d8b2a3d3618ccc38628f6d7b89ebfd8</id>
        <incarnation>1427714713</incarnation>
        <version>5.4</version>
        <uptime>44395</uptime>
        <poll>120</poll>
        <startdelay>0</startdelay>
        <localhostname>DMZ-Server</localhostname>
        <controlfile>/etc/monit/monitrc</controlfile>
        <httpd>
            <address>192.168.1.100</address>
            <port>2812</port>
            <ssl>0</ssl>
        </httpd>
    </server>
    <platform>
        <name>Linux</name>
        <release>2.6.32-34-pve</release>
        <version>#1 SMP Sat Nov 8 09:38:26 CET 2014</version>
        <machine>i686</machine>
        <cpu>8</cpu>
        <memory>3145728</memory>
        <swap>1048576</swap>
    </platform>
    <service type="3">
        <name>mmonit</name>
        <collected_sec>1427759050</collected_sec>
        <collected_usec>180381</collected_usec>
        <status>0</status>
        <status_hint>0</status_hint>
        <monitor>1</monitor>
        <monitormode>0</monitormode>
        <pendingaction>0</pendingaction>
        <pid>11481</pid>
        <ppid>1</ppid>
        <uptime>692522</uptime>
        <children>0</children>

2 个答案:

答案 0 :(得分:0)

任何树遍历算法都可以解决问题。

http://rosettacode.org/wiki/Tree_traversal#Python

我会坚持使用XML并使用lxml来解析和遍历XML树。

http://lxml.de/tutorial.html
http://lxml.de/tutorial.html#the-elementtree-class

我相信其他人会建议更新的XML库,随意使用它们。 LXML是我唯一熟悉的。

答案 1 :(得分:0)

对于搜索和提取,我建议跳过字典并直接处理XML“直接”。 XPath是一个被证明是非常强大的概念,可以遍历并获取XML文档的特定部分。例如,要在XML文档中的任何位置获取<service>元素,您只需在XPath中说://service

另一个答案中提到的

LXML是python中support XPath的一个可能的库选项。例如:

from lxml import etree
xml_source = """<root>
    <server>
        <id>9d8b2a3d3618ccc38628f6d7b89ebfd8</id>
        <incarnation>1427714713</incarnation>
        <version>5.4</version>
        <uptime>44395</uptime>
        <poll>120</poll>
        <startdelay>0</startdelay>
        <localhostname>DMZ-Server</localhostname>
        <controlfile>/etc/monit/monitrc</controlfile>
        <httpd>
            <address>192.168.1.100</address>
            <port>2812</port>
            <ssl>0</ssl>
        </httpd>
    </server>
    <platform>
        <name>Linux</name>
        <release>2.6.32-34-pve</release>
        <version>#1 SMP Sat Nov 8 09:38:26 CET 2014</version>
        <machine>i686</machine>
        <cpu>8</cpu>
        <memory>3145728</memory>
        <swap>1048576</swap>
    </platform>
    <service type="3">
        <name>mmonit</name>
        <collected_sec>1427759050</collected_sec>
        <collected_usec>180381</collected_usec>
        <status>0</status>
        <status_hint>0</status_hint>
        <monitor>1</monitor>
        <monitormode>0</monitormode>
        <pendingaction>0</pendingaction>
        <pid>11481</pid>
        <ppid>1</ppid>
        <uptime>692522</uptime>
        <children>0</children>
    </service>
</root>"""

doc = etree.fromstring(xml_source)
service = doc.find('.//service')
#you can then operate on service as needed: 
#parse it to dictionary, or in this example print the markup
print(etree.tostring(service, pretty_print=True))