Python3 XML处理模块详解

news2024/11/24 13:31:00

目录

一:XML文件格式

二:ElementTree解析XML文件

三:Element之查找

四:Element之修改

五:Element之删除

六:Element之增加


         xml是一种固有的分层数据格式,最自然的表示方式是解析成树状,在配置文件中很多采用xml的形式进行配置存储。在xml的日常维护中,经常会涉及到对xml文件的增删改查,如果从零开始对xml进行硬解析也是一件很麻烦的事情。

        Python3内置了xml处理模块xml.etree.ElementTree 可以帮助我们去解析xml,并支持对xml的增删改查。下面我们对该模块从增删改查四个方面进行探索

一:XML文件格式

        xml总体看上去就是一个树状的分层结构,下面给出一个xml文件的样例,后面针对xml的增删改查操作就以该xml为例:

<?xml version="1.0" encoding="utf-8"?>
<addr_info id="中国">
   <R1 type="上海">
       <device_type>黄埔区</device_type>
       <username>admin</username>
       <people_num>一百万</people_num>
       <company>zte.com.cn</company>
   </R1>
   <SW3 type="南京">
       <device_type>江宁区</device_type>
       <username>admin</username>
       <people_num>两百万</people_num>
       <company>baidu.com.cn</company>
   </SW3>
</addr_info>

二:ElementTree解析XML文件

我们用ElementTree去解析上面的xml文件,具体用法如下:

import xml.etree.ElementTree as ET


tree = ET.parse('eg.xml')#直接读取xml文件,形成ElementTree结构
root = tree.getroot() # 获取root tag
print('tag:',root.tag) # 打印root的tag
print('attrib:',root.attrib) # 打印root的attrib
# 使用root索引访问标签的值,[0]是R1标签,[0]是R1标签中的第一个标签device_type, .text是取这个标签的值,自然值就是cisco_ios
print(root[0][0].text)

for child in root: # 打印root的child层的tag和attrib
   print(child.tag, child.attrib)

运行结果:

tag: addr_info
attrib: {'id': '中国', 'topic': 'ftz'}
黄埔区
R1 {'type': '上海'}
SW3 {'type': '南京'}

我们可以通过dir来查看root支持的属性

['__class__', '__copy__', '__deepcopy__', '__delattr__', '__delitem__',
 '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__',
 '__getitem__', '__getstate__', '__gt__', '__hash__', '__init__', 
'__init_subclass__', '__le__', '__len__', '__lt__', '__ne__', '__new__', 
'__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__setitem__', 
'__setstate__', '__sizeof__', '__str__', '__subclasshook__', 'append', 'attrib',
 'clear', 'extend', 'find', 'findall', 'findtext', 'get', 'getchildren', 
'getiterator', 'insert', 'items', 'iter', 'iterfind', 'itertext', 'keys', 
'makeelement', 'remove', 'set', 'tag', 'tail', 'text']

三:Element之查找

Element有很丰富的查找方法,总结如下:

iter(tag=None) 遍历Element的child,可以指定tag精确查找
findall(match) 查找当前元素tag或path能匹配的child节点
find(match) 查找当前元素tag或path能匹配的第一个child节点
get(key, default=None) 获取元素指定key对应的attrib,如果没有attrib,返回default。 

我们用iter和findall为例来查找上述例子中的人口

import xml.etree.ElementTree as ET


tree = ET.parse('eg.xml')
root = tree.getroot()

#iter查找
for addr in root.iter():
    if addr.tag == 'people_num':
        print("people_num=",addr.text)

#findall查找
for people in root.findall('R1'):
    peopleNum = people.find('people_num').text
    print("people_num=",peopleNum)

for people in root.findall('SW3'):
    peopleNum = people.find('people_num').text
    print("people_num=",peopleNum)

运行结果:

四:Element之修改

Element的修改方法如下:

Element.text 直接修改字段
Element.remove() 删除字段
Element.set() 添加或修改属性attrib
with Element.append() 添加新的child 

我们将上海黄浦区的人口数从一百万改成一千万

import xml.etree.ElementTree as ET


tree = ET.parse('eg.xml')
root = tree.getroot()


for addr in root.iter('R1'):
    addr.find('people_num').text = '一千万'

tree.write('./eg2.xml',encoding='utf-8')

确认修改完毕后,可以使用ElementTree.write()方法写入

五:Element之删除

Element的删除方法如下:

remove  移除节点

我们还是以上面为例,删除整个SW3节点

import xml.etree.ElementTree as ET


tree = ET.parse('eg.xml')
root = tree.getroot()

for addr in root.findall('SW3'):
    root.remove(addr)

tree.write('./eg2.xml',encoding='utf-8')

那如果我想删除R1节点的子节点username呢,还没摸索出来,后续更新

六:Element之增加

Element的增加节点方法如下:

ET.SubElement

我们新增一个节点黄冈的节点,还有节点下面的子节点,方法如下:

import xml.etree.ElementTree as ET


xmlParse = ET.parse('eg.xml')
root = xmlParse.getroot()
tree = ET.ElementTree(root)

#增加R3节点
hubeiNode = ET.SubElement(root,'R3')
hubeiNode.attrib = {'type':'黄冈'}
#增加R3节点的子节点

huanggang = ET.SubElement(hubeiNode,'device_type')
huanggang.text = '黄梅县'

huanggang2 = ET.SubElement(hubeiNode,'username')
huanggang2.text = 'admin'

huanggang3 = ET.SubElement(hubeiNode,'people_num')
huanggang3.text = '五十万'

huanggang4 = ET.SubElement(hubeiNode,'company')
huanggang4.text = 'feidadun.com'

tree.write('./eg2.xml', encoding='utf-8', xml_declaration=True, short_empty_elements=True)

虽然达到了我们的目的,但是写入后都挤到一行了,不方便看,用下面的函数进行美化

def pretty_xml(element, indent, newline, level=0):  # elemnt为传进来的Elment类,参数indent用于缩进,newline用于换行
    if element:  # 判断element是否有子元素
        if (element.text is None) or element.text.isspace():  # 如果element的text没有内容
            element.text = newline + indent * (level + 1)
        else:
            element.text = newline + indent * (level + 1) + element.text.strip() + newline + indent * (level + 1)
            # else:  # 此处两行如果把注释去掉,Element的text也会另起一行
            # element.text = newline + indent * (level + 1) + element.text.strip() + newline + indent * level
    temp = list(element)  # 将element转成list
    for subelement in temp:
        if temp.index(subelement) < (len(temp) - 1):  # 如果不是list的最后一个元素,说明下一个行是同级别元素的起始,缩进应一致
            subelement.tail = newline + indent * (level + 1)
        else:  # 如果是list的最后一个元素, 说明下一行是母元素的结束,缩进应该少一个
            subelement.tail = newline + indent * level
        pretty_xml(subelement, indent, newline, level=level + 1)  # 对子元素进行递归操作

最后的效果如下:

附上全部代码:

import xml.etree.ElementTree as ET


def pretty_xml(element, indent, newline, level=0):  # elemnt为传进来的Elment类,参数indent用于缩进,newline用于换行
    if element:  # 判断element是否有子元素
        if (element.text is None) or element.text.isspace():  # 如果element的text没有内容
            element.text = newline + indent * (level + 1)
        else:
            element.text = newline + indent * (level + 1) + element.text.strip() + newline + indent * (level + 1)
            # else:  # 此处两行如果把注释去掉,Element的text也会另起一行
            # element.text = newline + indent * (level + 1) + element.text.strip() + newline + indent * level
    temp = list(element)  # 将element转成list
    for subelement in temp:
        if temp.index(subelement) < (len(temp) - 1):  # 如果不是list的最后一个元素,说明下一个行是同级别元素的起始,缩进应一致
            subelement.tail = newline + indent * (level + 1)
        else:  # 如果是list的最后一个元素, 说明下一行是母元素的结束,缩进应该少一个
            subelement.tail = newline + indent * level
        pretty_xml(subelement, indent, newline, level=level + 1)  # 对子元素进行递归操作

xmlParse = ET.parse('eg.xml')
root = xmlParse.getroot()
tree = ET.ElementTree(root)

#增加R3节点
hubeiNode = ET.SubElement(root,'R3')
hubeiNode.attrib = {'type':'黄冈'}
#增加R3节点的子节点

huanggang = ET.SubElement(hubeiNode,'device_type')
huanggang.text = '黄梅县'

huanggang2 = ET.SubElement(hubeiNode,'username')
huanggang2.text = 'admin'

huanggang3 = ET.SubElement(hubeiNode,'people_num')
huanggang3.text = '五十万'

huanggang4 = ET.SubElement(hubeiNode,'company')
huanggang4.text = 'feidadun.com'

pretty_xml(root, '  ', '\n')  # 执行美化方法    缩进为两个空格,'\n'换行
tree.write('./eg2.xml', encoding='utf-8', xml_declaration=True, short_empty_elements=True)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1005758.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

基于springboot实现的最便捷的解析word文档

概述 导入excel或word是一些web应用常见的需求&#xff0c;本demo详细介绍怎么导入word,读取word里面的数据 详细 一、运行效果 二、实现过程 ①、首先用maven快速搭建一个spring boot 项目 <properties><project.build.sourceEncoding>UTF-8</project.buil…

unity 使用Photon进行网络同步

Pun使用教程 第一步&#xff1a;请确保使用的 Unity 版本等于或高于 2017.4&#xff08;不建议使用测试版&#xff09;创建一个新项目。 第二步&#xff1a;打开资源商店并找到 PUN 2 资源并下载/安装它。 导入所有资源后&#xff0c;让 Unity 重新编译。 第三步&#xf…

stm32---外部中断

一、EXTI STM32F10x外部中断/事件控制器&#xff08;EXTI&#xff09;包含多达20个用于产生事件/中断请求的边沿检测器。EXTI的每根输入线都可单独进行配置&#xff0c;以选择类型&#xff08;中断或事件&#xff09;和相应的触发事件&#xff08;上升沿触发、下降沿触发…

深入理解JVM虚拟机第四篇:一些常用的JVM虚拟机

一&#xff1a;Sun Classic VM虚拟机 早在1996年Java1.0版本的时候&#xff0c;Sun公司发布了一款名为Sun classic VM的Java虚拟机&#xff0c;它同时也是世界上第一款商用Java虚拟机&#xff0c;JDK1.4时完全被淘汰。 现在hotspot内置了此虚拟机。 这款虚拟机内部只提供解释器…

入门人工智能 ——使用 tensorflow 训练一个新闻分类模型(6)

入门人工智能 ——使用 tensorflow 训练一个新闻分类模型&#xff08;6&#xff09; 入门人工智能 ——使用 tensorflow 训练一个新闻分类模型使用 tensorflow 训练一个新闻分类模型1. 安装TensorFlow和所需的依赖项。2. 打开收集的新闻数据集构建模型模型训练模型评估保存模型…

hadoop启动报错:Attempting to operate on hdfs namenode as root

在hadoop安装路径的 /hadoop/sbin路径下&#xff1a; 将start-dfs.sh&#xff0c;stop-dfs.sh两个文件顶部添加以下参数 #!/usr/bin/env bash HDFS_DATANODE_USERroot HADOOP_SECURE_DN_USERhdfs HDFS_NAMENODE_USERroot HDFS_SECONDARYNAMENODE_USERroot还有&#xff0c;star…

基于STM32+华为云IOT设计的智能窗帘控制系统

一、项目背景 随着智能家居技术的不断发展&#xff0c;人们对于家居生活的需求也越来越高。智能窗帘作为智能家居领域的重要组成部分&#xff0c;为用户提供了更便捷、舒适的生活体验。本项目基于STM32主控芯片和华为云物联网平台&#xff0c;设计一款智能窗帘控制系统&#x…

学习记忆——宫殿篇——记忆宫殿——记忆桩——知识讲解

类比 假设这些桩子好比不同的交通工具&#xff0c;每一种交通工具都可以助我们到达目的地&#xff0c;那举现在就根据你的时间以及现实情况&#xff0c;选择最合适自己的交通工具即可&#xff0c;重点在于你要熟悉每种交通工具的用途不区别。桩子也是如此&#xff0c;把所有的桩…

pat多项式求和

idea 权重记得也是浮点数&#xff0c;否则2&#xff0c;5测试点不过 solution #include <stdio.h> int main(){int n ;double x0, ans 0, power 1;scanf("%d%lf", &n, &x0);double a[n1];for(int i 0; i < n; i)scanf("%lf", a i)…

Docker+jenkinsPipeline运行实现python自动化测试(超详细)

一、实现思路 在 Linux 服务器安装 docker创建 jenkins 容器jenkins 中创建 pipeline 项目根据自动化项目依赖包构建 python 镜像(构建自动化 python 环境)运行新的 python 容器&#xff0c;执行 jenkins 从仓库中拉下来的自动化项目执行完成之后删除容器 二、环境准备 Linu…

Java基础入门·多线程·线程池ThreadPool篇

前言 特点分析 线程池ThreadPool 销毁线程池 Executor类 ​​​​​​​ ​​​​​​​ ​​​​​​​ Callable接口 线程池使用 ​​​​​​​…

全面详解Maven的配置文件pom.xml(含常用plugin)

系列文章目录 手把手教你maven的安装与配置(windows) 全面详解Maven的配置文件pom.xml&#xff08;含常用plugin&#xff09; 系列文章目录一、什么是pom.xml二、pom.xml的结构三、项目的基本信息1.modules2.parent3.scm4.properties 四、项目的依赖列表1.dependency2.reposit…

【Cocos Creator 3.5实现赛车游戏】10.实现汽车节点的运动逻辑

转载知识星球 | 深度连接铁杆粉丝&#xff0c;运营高品质社群&#xff0c;知识变现的工具 项目地址&#xff1a;赛车小游戏-基于Cocos Creator 3.5版本实现: 课程的源码&#xff0c;基于Cocos Creator 3.5版本实现 上一节的学习后&#xff0c;您已经完成了对汽车节点的控制逻…

数字IC设计之时序分析基础概念汇总

1 时钟Clock 理想的时钟模型是一个占空比为50%且周期固定的方波。时钟是FPGA中同步电路逻辑运行的一个基准。理想的时钟信号如下图: 2 时钟抖动Clock Jitter 理想的时钟信号是完美的方波&#xff0c;但是实际的方波是存在一些时钟抖动的。那么什么是时钟抖动呢?时钟抖动&#…

(2)数据库mongodb 终端 和 vscode创建数据库 数据导入导出

可视化工具&#xff1a; Robo 3T | Free, open-source MongoDB GUI (formerly Robomongo) mongodb安装官网&#xff1a;MongoDB: The Developer Data Platform | MongoDB 文档&#xff1a;安装 MongoDB - MongoDB-CN-Manual (mongoing.com) 配置环境变量&#xff1a; 是为了扩…

【图论】有向图的强连通分量

算法提高课笔记&#xff08;本篇未更新完 还有俩例题&#xff09; 文章目录 理论基础SCC板子 例题受欢迎的牛题意思路代码 学校网络题意思路代码 理论基础 什么是连通分量&#xff1f; 对于一个有向图&#xff0c;分量中任意两点u&#xff0c;v&#xff0c;必然可以从u走到v…

跑步运动耳机哪个牌子好、推荐几款专业跑步耳机

跑步是一项简单的运动&#xff0c;只要交替迈左右腿就能进行。然而&#xff0c;跑步也可能会变得单调乏味。即使是意志坚定、热爱跑步的人&#xff0c;在这漫长的过程中也会感到乏味&#xff0c;更不用说像你我这样的普通跑者了。音乐能够让跑步这项运动变得有趣起来&#xff0…

前端自适应瀑布流布局

JS案例自适应瀑布流 &#x1f31f;效果预览 &#x1f31f;什么是瀑布流 &#x1f31f;制作思路 &#x1f31f;具体实现 页面结构 js代码实现 &#x1f31f;写在最后 &#x1f31f;效果预览 前端自适应瀑布流效果预览 &#x1f31f;什么是瀑布流 瀑布流&#xff0c;又…

prize_p1

文章目录 解题过程代码审计思路问题解决数组绕过preg_match__destruct的触发修改phar文件以及签名phar://支持的后缀 题解方法一&#xff08;数组绕过&#xff09;方法二&#xff08;gzip绕过&#xff09; 解题过程 源代码 <META http-equiv"Content-Type" conte…

3D人体生成名人堂

一、马普所认知系统实验室。 Perceiving Systems - Max Planck Institute for Intelligent SystemsUsing computer vision, computer graphics, and machine learning, we teach computers to see people and understand their behavior in complex 3D scenes. We are located…