python--XML

什么是XML?

XML 指可扩展标记语言(eXtensible Markup Language)。

XML 被设计用来传输和存储数据。

XML是一套定义语义标记的规则,这些标记将文档分成许多部件并对这些部件加以标识。

它也是元标记语言,即定义了用于定义其他与特定领域有关的、语义的、结构化的标记语言的句法语言。

python对XML的解析

常见的XML编程接口有DOM和SAX,这两种接口处理XML文件的方式不同,当然使用场合也不同。

python有三种方法解析XML,SAX,DOM,以及ElementTree:

1.SAX (simple API for XML )

python 标准库包含SAX解析器,SAX用事件驱动模型,通过在解析XML的过程中触发一个个的事件并调用用户定义的回调函数来处理XML文件。

2.DOM(Document Object Model)

将XML数据在内存中解析成一个树,通过对树的操作来操作XML。

3.ElementTree(元素树)

ElementTree就像一个轻量级的DOM,具有方便友好的API。代码可用性好,速度快,消耗内存少。

注:因DOM需要将XML数据映射到内存中的树,一是比较慢,二是比较耗内存,而SAX流式读取XML文件,比较快,占用内存少,但需要用户实现回调函数(handler)。

准备一份XML格式的文件:

<?xml version="1.0"?>
<data>
    <country name="Liechtenstein">
        <rank>1</rank>
        <year>2008</year>
        <gdppc>141100</gdppc>
        <neighbor name="Austria" direction="E"/>
        <neighbor name="Switzerland" direction="W"/>
    </country>
    <country name="Singapore">
        <rank>4</rank>
        <year>2011</year>
        <gdppc>59900</gdppc>
        <neighbor name="Malaysia" direction="N"/>
    </country>
    <country name="Panama">
        <rank>68</rank>
        <year>2011</year>
        <gdppc>13600</gdppc>
        <neighbor name="Costa Rica" direction="W"/>
        <neighbor name="Colombia" direction="E"/>
    </country>
</data>

XML文件格式介绍:

<tag attrib = > text </tag> tail

例:<APP_KEY channel = 'CSDN'> hello123456789 </APP_KEY>

  • tag,即标签,用于标识该元素表示哪种数据,即APP_KEY
  • attrib,即属性,用Dictionary形式保存,即{'channel' = 'CSDN'}
  • text,文本字符串,可以用来存储一些数据,即hello123456789
  • tail,尾字符串,并不是必须的,例子中没有包含。

ElementTree解析XML文件的过程:

  • 导入ElementTree,import xml.etree.ElementTree as ET
  • 解析Xml文件找到根节点:
  • 直接解析XML文件并获得根节点,tree = ET.parse('country_data.xml') root = tree.getroot()
  • 解析字符串,root = ET.fromstring(country_data_as_string)
  • 遍历根节点可以获得子节点,然后就可以根据需求拿到需要的字段了。

    源码演示:

    示例代码:

    #!usr/bin/python
    # -*- coding: utf-8 -*-
    #==========================
    import xml.etree.ElementTree as ET
    tree = ET.parse('country_data.xml')
    root = tree.getroot()
    print('root-tag:',root.tag,',root-attrib:',root.attrib,',root-text:',root.text)
    for child in root:
         print('child-tag是:',child.tag,',child.attrib:',child.attrib,',child.text:',child.text)
         for sub in child:
              print('sub-tag是:',sub.tag,',sub.attrib:',sub.attrib,',sub.text:',sub.text)
    

    运行结果:

    >>> 
    root-tag: data ,root-attrib: {} ,root-text: 
        
    child-tag是: country ,child.attrib: {'name': 'Liechtenstein'} ,child.text: 
            
    sub-tag是: rank ,sub.attrib: {} ,sub.text: 1
    sub-tag是: year ,sub.attrib: {} ,sub.text: 2008
    sub-tag是: gdppc ,sub.attrib: {} ,sub.text: 141100
    sub-tag是: neighbor ,sub.attrib: {'direction': 'E', 'name': 'Austria'} ,sub.text: None
    sub-tag是: neighbor ,sub.attrib: {'direction': 'W', 'name': 'Switzerland'} ,sub.text: None
    child-tag是: country ,child.attrib: {'name': 'Singapore'} ,child.text: 
            
    sub-tag是: rank ,sub.attrib: {} ,sub.text: 4
    sub-tag是: year ,sub.attrib: {} ,sub.text: 2011
    sub-tag是: gdppc ,sub.attrib: {} ,sub.text: 59900
    sub-tag是: neighbor ,sub.attrib: {'direction': 'N', 'name': 'Malaysia'} ,sub.text: None
    child-tag是: country ,child.attrib: {'name': 'Panama'} ,child.text: 
            
    sub-tag是: rank ,sub.attrib: {} ,sub.text: 68
    sub-tag是: year ,sub.attrib: {} ,sub.text: 2011
    sub-tag是: gdppc ,sub.attrib: {} ,sub.text: 13600
    sub-tag是: neighbor ,sub.attrib: {'direction': 'W', 'name': 'Costa Rica'} ,sub.text: None
    sub-tag是: neighbor ,sub.attrib: {'direction': 'E', 'name': 'Colombia'} ,sub.text: None
    

    查找指定的子节点:

    当XML文件较大或者其中的子节点tag非常多的时候,一个一个获取是比较麻烦的而且有很多不是我们需要的,这样我们可以通过find('nodeName')或者findall('nodeName')方法来查找指定tag的节点。

    • find('nodeName'):表示在该节点下,查找其中第一个tag为nodeName的节点。
    • findall('nodeName'):表示在该节点下,查找其中所有tag为nodeName的节点。

    代码示例:

    #!usr/bin/python
    # -*- coding: utf-8 -*-
    import xml.etree.ElementTree as ET
    tree = ET.parse('country_data.xml')
    root = tree.getroot()
    animNode = root.find('country') #查找root节点下第一个tag为country的节点
    print(animNode.tag,animNode.attrib,animNode.text)
    

    运行结果,可以在XML文件中看到,第一个tag为country的节点确实是Liechtenstein:

    >>> 
    country {'name': 'Liechtenstein'} 
    

    删除指定的节点以及保存

    在合并Manifest文件的时候,可能有一些重复的权限,那么怎么删除掉呢,删除指定节点可以通过remove(node)方法,移除指定的节点。
    代码示例,比如我们想移除attribute中name为Liechtenstein的节点:

    #!usr/bin/python
    # -*- coding: utf-8 -*-
    import xml.etree.ElementTree as ET
    tree = ET.parse('country_data.xml')
    root = tree.getroot()
    animNode = root.find('country') 
    if animNode.attrib['name'] == 'Liechtenstein':
         root.remove(animNode)
    tree.write('finish.xml')#保存修改后的XML文件
    

    运行结果,我们打开保存的finish.xml文件,发现保存结果如下,name为Liechtenstein的节点已经被删除了:

    <data>
        <country name="Singapore">
            <rank>4</rank>
            <year>2011</year>
            <gdppc>59900</gdppc>
            <neighbor direction="N" name="Malaysia" />
        </country>
        <country name="Panama">
            <rank>68</rank>
            <year>2011</year>
            <gdppc>13600</gdppc>
            <neighbor direction="W" name="Costa Rica" />
            <neighbor direction="E" name="Colombia" />
        </country>
    </data>

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值