使用python编辑XML文件

XML(Extensible Markup Language)即可扩展标记语言,它可以用来标记数据、定义数据类型,是一种允许用户对自己的标记语言进行定义的源语言。从结构上,它很像我们常见的HTML超文本标记语言。但他们被设计的目的是不同的,超文本标记语言被设计用来显示数据,其焦点是数据的外观。它被设计用来传输存储数据,其焦点是数据的内容

特点
  • 自定义标签对组成,<aa></aa>
  • 标签可以有属性:<aa id='123'></aa>
  • 标签对可以嵌入数据:<aa>abc</aa>
  • 标签可以嵌入子标签(具有层级关系)
结构

xml文件可以理解为一个树结构,有根结点,子结点的概念。每个结点元素(包含结点名、属性和数据。


xml结构示意图

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


python 使用 SAX 解析 xml

SAX 是一种基于事件驱动的 API。
利用 SAX 解析 XML 文档牵涉到两个部分: 解析器和事件处理器。
解析器负责读取 XML 文档, 并向事件处理器发送事件, 如元素开始跟元素结束事件;
而事件处理器则负责对事件作出相应, 对传递的 XML 数据进行处理。
1、对大型文件进行处理;
2、只需要文件的部分内容,或者只需从文件中得到特定信息。
3、想建立自己的对象模型的时候。
在 python 中使用 sax 方式处理 xml 要先引入 xml.sax 中的 parse 函数,还有 xml.sax.handler 中的 ContentHandler。

参考

https://docs.python.org/3.7/library/xml.sax.html


python使用 xml.dom 解析 xml

文件对象模型(Document Object Model,简称 DOM),是 W3C 组织推荐的处理可扩展置标语言的标准编程接口。
一个 DOM 的解析器在解析一个 XML 文档时,一次性读取整个文档,把文档中所有元素保存在内存中的一个树结构里,之后你可以利用 DOM 提供的不同的函数来读取或修改文档的内容和结构,也可以把修改过的内容写入 xml 文件。python 中用x ml.dom.minidom 来解析 xml 文件,实例如下:

参考

https://docs.python.org/3.7/library/xml.dom.minidom.html?highlight=xml%20dom#module-xml.dom.minidom

XML示例
<?xml version="1.0" encoding="utf-8"?>
<postgresql>
    <connection>
        <pg_host>localhost</pg_host>
        <pg_port>5432</pg_port>
    </connection>
</postgresql>
对应python示例

对xml文件中标签的值进行读取、修改、写入

import  xml.dom.minidom #mxl.dom.minidom 模块被用来处理xml文件,所以要先引入
import os

def Change_param(filepath):
    #打开xml文档
    dom = xml.dom.minidom.parse(filepath) #ml.dom.minidom.parse() 用于打开一个xml文件,并将这个文件对象dom变量。
    root = dom.documentElement #documentElement 用于得到dom对象的文档元素,并把获得的对象给root
    #每一个结点都有它的nodeName,nodeValue,nodeType属性。
    print (root.nodeName) # nodeName为结点名字

    #获得root的子标签以的标签,对于知道名字的子标签,可以使用getElementsByTagName方法获取
    #getElementsByTagName('tablist') 获取的是一个相同名称的标签列表,tablist[0]表示表示第一个
    connection = root.getElementsByTagName('connection')
    Hostlist = connection[0].getElementsByTagName('pg_host')
    Portlist = connection[0].getElementsByTagName('pg_port')
    posthost = Hostlist[0]
    postport =Portlist[0]
    print(posthost.firstChild.data)#改变前 
    print(postport.firstChild.data)
    posthost.firstChild.data = "1.0.0.127" # .data是结点的值
    postport.firstChild.data = "8080"
    print(posthost.firstChild.data)#改变后
    print(postport.firstChild.data)
    #存储结果
    with open('test.xml',"w") as f:
        dom.writexml(f)
if __name__ == '__main__':
    filepath="test.xml"
    Change_param(filepath)
运行结果

python使用 ElementTree解析 xml

python中用于解析xml文件的模块很多,相比于xml.dom,xml.sax等,ET模块提供了一个轻量级、Pythonic的API.简而言之,更快,更便捷,而且也够用。

参考

https://docs.python.org/3.7/library/xml.etree.elementtree.html

  • ElementTree.write("xmlfile"):更新xml文件
  • Element.append():为当前element对象添加子元素(element)
  • Element.set(key,value):为当前element的key属性设置value值
  • Element.remove(element):删除为element的节点
import xml.etree.ElementTree as ET
#创建根节点
root = ET.Element("postgresql")
#创建子节点,并添加属性
connection = ET.SubElement(root,"connection")
connection.attrib = {"key":"value"}
#创建子节点,并添加数据
pg_host = ET.SubElement(connection,"pg_host")
pg_host.text = "1.0.0.127"
pg_port = ET.SubElement(connection,"pg_port")
pg_port.text = "8080"
#创建结点,并添加入父节点中
book2 = ET.Element("book")
title2 = ET.SubElement(book2,"title")
title2.attrib = {"lang":"en"}
title2.text = "Harry Potter"
root.append(book2)
#创建elementtree对象,写文件
tree = ET.ElementTree(root)
tree.write("test2.xml")

#读取待修改文件
updateTree = ET.parse("test.xml")
root = updateTree.getroot()
#修改属性
connection = root.find("connection")
connection.set("key","new_value")
#修改title的数据值
phost = connection.find("pg_host")
print(phost.text)
phost.text = "Newhost"
print(phost.text)
#删除子结点
for book in root.findall("book"):
    if book.find("title").text == "Harry Potter":
        root.remove("book")
#写回原文件
updateTree.write("test2.xml")
运行结果
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容