Python利用ElementTree模块处理XML的方法详解


Posted in Python onAugust 31, 2017

前言

最近因为工作的需要,在使用 Python 来发送 SOAP 请求以测试 Web Service 的性能,由于 SOAP 是基于 XML 的,故免不了需要使用 python 来处理 XML 数据。在对比了几种方案后,最后选定使用 xml.etree.ElementTree 模块来实现。

这篇文章记录了使用 xml.etree.ElementTree 模块常用的几个操作,也算是总结一下,免得以后忘记了。分享出来也方法需要的朋友们参考学习,下面话不多说了,来一起看看详细的介绍吧。

概述

对比其他 Python 处理 XML 的方案,xml.etree.ElementTree 模块(下文我们以 ET 来表示)相对来说比较简单,接口也较友好。

官方文档 里面对 ET 模块进行了较为详细的描述,总的来说,ET 模块可以归纳为三个部分:ElementTree类,Element类以及一些操作 XML 的函数。

XML 可以看成是一种树状结构,ET 使用ElementTree类来表示整个 XML 文档,使用Element类来表示 XML 的一个结点。对整 XML 文档的操作一般是对ElementTree对象进行,而对 XML 结点的操作一般是对Element对象进行。

解析 XML 文件

ET 模块支持从一个 XML 文件构造ElementTree对象,例如我们的 XML 文件example.xml内容如下(下文会继续使用这个 XML 文档):

<?xml version="1.0" encoding="utf-8"?>
<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>
</data>

可以使用 ET 模块的parse()函数来从指定的 XML 文件构造一个ElementTree对象:

import xml.etree.ElementTree as ET

# 获取 XML 文档对象 ElementTree
tree = ET.parse('example.xml')
# 获取 XML 文档对象的根结点 Element
root = tree.getroot()
# 打印根结点的名称
print root.tag

从 XML 文件构造好ElementTree对象后,还可以获取其结点,或者再继续对结点进行进一步的操作。

解析 XML 字符串

ET 模块的fromstring()函数提供从 XML 字符串构造一个Element对象的功能。

xml_str = ET.tostring(root)
print xml_str
root = ET.fromstring(xml_str)
print root.tag

接着上面的代码,我们使用 ET 模块的tostring()函数来将上面我们构造的root对象转化为字符串,然后使用fromstring()函数重新构造一个Element对象,并赋值给root变量,这时root代表整个 XML 文档的根结点。

构造 XML

如果我们需要构造 XML 文档,可以使用 ET 模块的 Element类以及SubElement()函数。

可以使用Element类来生成一个Element对象作为根结点,然后使用ET.SubElement()函数生成子结点。

a = ET.Element('a')
b = ET.SubElement(a, 'b')
b.text = 'leehao.me'
c = ET.SubElement(a, 'c')
c.attrib['greeting'] = 'hello'
d = ET.SubElement(a, 'd')
d.text = 'www.leehao.me'
xml_str = ET.tostring(a, encoding='UTF-8')
print xml_str

输出:

<?xml version='1.0' encoding='UTF-8'?>
<a><b>leehao.me</b><c greeting="hello" /><d>www.leehao.me</d></a>

如果需要输出到文件中,可以继续使用ElementTree.write()方法来处理:

# 先构造一个 ElementTree 以便使用其 write 方法
tree = ET.ElementTree(a)
tree.write('a.xml', encoding='UTF-8')

执行后,便会生成一个 XML 文件a.xml:

<?xml version='1.0' encoding='UTF-8'?>
<a><b>leehao.me</b><c greeting="hello" /><d>www.leehao.me</d></a>

XML 结点的查找与更新

1. 查找 XML 结点

Element类提供了Element.iter()方法来查找指定的结点。Element.iter()会递归查找所有的子结点,以便查找到所有符合条件的结点。

# 获取 XML 文档对象 ElementTree
tree = ET.parse('example.xml')
# 获取 XML 文档对象的根结点 Element
root = tree.getroot()
# 递归查找所有的 neighbor 子结点
for neighbor in root.iter('neighbor'):
 print neighbor.attrib

输出:

{'direction': 'E', 'name': 'Austria'}
{'direction': 'W', 'name': 'Switzerland'}
{'direction': 'N', 'name': 'Malaysia'}

如果使用Element.findall()或者Element.find()方法,则只会从结点的直接子结点中查找,并不会递归查找。

for country in root.findall('country'):
 rank = country.find('rank').text
 name = country.get('name')
 print name, rank

输出:

Liechtenstein 1
Singapore 4

2. 更新结点

如果需要更新结点的文本,可以通过直接修改Element.text来实现。如果需要更新结点的属性,可以通过直接修改Element.attrib来实现。

对结点进行更新后,可以使用ElementTree.write()方法将更新后的 XML 文档写入文件中。

# 获取 XML 文档对象 ElementTree
tree = ET.parse('example.xml')
# 获取 XML 文档对象的根结点 Element
root = tree.getroot()
for rank in root.iter('rank'):
 new_rank = int(rank.text) + 1
 rank.text = str(new_rank)
 rank.attrib['updated'] = 'yes'
tree.write('output.xml', encoding='UTF-8')

新生成的output.xml文件以下:

<?xml version='1.0' encoding='UTF-8'?>
<data>
 <country name="Liechtenstein">
  <rank updated="yes">2</rank>
  <year>2008</year>
  <gdppc>141100</gdppc>
  <neighbor direction="E" name="Austria" />
  <neighbor direction="W" name="Switzerland" />
 </country>
 <country name="Singapore">
  <rank updated="yes">5</rank>
  <year>2011</year>
  <gdppc>59900</gdppc>
  <neighbor direction="N" name="Malaysia" />
 </country>
</data>

对比example.xml文件,可以看到output.xml文件已更新。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持。

参考资料

  • https://docs.python.org/2/library/xml.html#xml-vulnerabilities
  • https://stackoverflow.com/questions/1912434/how-do-i-parse-xml-in-python
Python 相关文章推荐
python类定义的讲解
Nov 01 Python
Python中使用Boolean操作符做真值测试实例
Jan 30 Python
Python求两个文本文件以行为单位的交集、并集与差集的方法
Jun 17 Python
详解Python中的日志模块logging
Jun 19 Python
深入理解python try异常处理机制
Jun 01 Python
Python学习小技巧之列表项的推导式与过滤操作
May 20 Python
Python爬虫实现百度图片自动下载
Feb 04 Python
Python 实现遥感影像波段组合的示例代码
Aug 04 Python
Python接口测试文件上传实例解析
May 22 Python
Pycharm github配置实现过程图解
Oct 13 Python
给numpy.array增加维度的超简单方法
Jun 02 Python
python机器学习创建基于规则聊天机器人过程示例详解
Nov 02 Python
go和python变量赋值遇到的一个问题
Aug 31 #Python
理解Python中的绝对路径和相对路径
Aug 30 #Python
python 递归遍历文件夹,并打印满足条件的文件路径实例
Aug 30 #Python
python递归打印某个目录的内容(实例讲解)
Aug 30 #Python
python-opencv在有噪音的情况下提取图像的轮廓实例
Aug 30 #Python
关于python的list相关知识(推荐)
Aug 30 #Python
Python编程实现正则删除命令功能
Aug 30 #Python
You might like
第十二节--类的自动加载
2006/11/16 PHP
PHP开发框架总结收藏
2008/04/24 PHP
Function eregi is deprecated (解决方法)
2013/06/21 PHP
PHP的引用详解
2015/02/22 PHP
php解析xml方法实例详解
2015/05/12 PHP
php将字符串随机分割成不同长度数组的方法
2015/06/01 PHP
php动态绑定变量的用法
2015/06/16 PHP
PHP执行系统命令函数实例讲解
2021/03/03 PHP
JavaScript入门教程(3) js面向对象
2009/01/31 Javascript
分享8款优秀的 jQuery 加载动画和进度条插件
2012/10/24 Javascript
js图片延迟加载的实现方法及思路
2013/07/22 Javascript
jquery利用ajax调用后台方法实例
2013/08/23 Javascript
jquery中使用循环下拉菜单示例代码
2014/09/24 Javascript
Jquery EasyUI Datagrid右键菜单实现方法
2016/12/30 Javascript
ES6新特性八:async函数用法实例详解
2017/04/21 Javascript
vue组件发布到npm简单步骤
2017/11/30 Javascript
VS Code转换大小写、修改选中文字或代码颜色的方法
2017/12/15 Javascript
three.js实现3D模型展示的示例代码
2017/12/31 Javascript
ES6 Map结构的应用实例分析
2019/06/26 Javascript
解决layui弹出层layer的area过大被遮挡的问题
2019/09/21 Javascript
CountUp.js实现数字滚动增值效果
2019/10/17 Javascript
Python cookbook(数据结构与算法)将名称映射到序列元素中的方法
2018/03/22 Python
tensorflow 1.0用CNN进行图像分类
2018/04/15 Python
Python爬虫之正则表达式的使用教程详解
2018/10/25 Python
Python钉钉报警及Zabbix集成钉钉报警的示例代码
2020/08/17 Python
EMU Australia澳大利亚官网:澳大利亚本土雪地靴品牌
2019/07/24 全球购物
澳大利亚二手奢侈品网站:Modsie
2019/09/23 全球购物
鲜果饮品店创业计划书
2014/01/21 职场文书
运动会解说词200字
2014/02/06 职场文书
镇政府副镇长群众路线专题民主生活会对照检查材料
2014/09/19 职场文书
教育实践活动对照检查材料
2014/09/23 职场文书
公司客户答谢酒会祝酒词
2015/08/11 职场文书
创业计划书之电动车企业
2019/10/11 职场文书
详解Nginx启动失败的几种错误处理
2021/04/01 Servers
抖音动画片,皮皮虾,《治愈系》动画在用这首REMIX作为背景音乐,Anak ,The last world with you完整版
2022/03/16 杂记
动漫APP软件排行榜前十名,半次元上榜,第一款由腾讯公司推出
2022/03/18 杂记