Python读写xml文件

Python读写xml文件,第1张

Python读写xml文件
    • xml文件知识点
    • 读取xml文件
    • 写入xml文件
    • VOC数据集类别提取

最近需要提取VOC数据集中的特定类别,所以就学习一下xml文件的读取和写入,毕竟xml格式的标签在目标检测中还是用的比较多的

参考博客:
https://blog.csdn.net/hu694028833/article/details/81089959
https://blog.csdn.net/wsp_1138886114/article/details/86576900

xml文件知识点

主要学习 基于ElementTree
XML是可扩展标记语言(Extensible Markup Language)的缩写,其中标记是关键部分。


用户可以创建内容,然后使用限定标记标记它,从而使每个单词、短语或块成为可识别、可分类的信息。



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


DOM是由W3C官方提出的标准,它会把整个XML文件读入内存,并将该文件解析成树,我们可以通过访问树的节点的方式访问XML中的标签,但是这种方法占用内存大,解析慢,如果读入文件过大,尽量避免使用这种方法。


SAX是事件驱动的,通过在解析XML的过程中触发一个个的事件并调用用户自定义的回调函数来处理XML文件,速度比较快,占用内存少,但是需要用户实现回调函数,因此Python标准库的官方文档中这样介绍SAX:SAX每次只允许你查看文档的一小部分,你无法通过当前获取的元素访问其他元素。


Python中提供了很多包支持XML文件的解析,如xml.dom,xml.sax,xml.dom.minidom和xml.etree.ElementTree等

读取xml文件

读取文档:tree = ET.parse(‘test.xml’)
获得根节点:root = tree.getroot()
获得所有子节点:list(root)
查找子节点,注意这里不会递归查找所有子节点:root.findall(‘object’)
查找子节点,递归查找所有子节点:root.iter(‘object’)
查看节点名称:root.tag

写入xml文件

创建节点:root = ET.Element(‘Root’)
创建文档:tree = ET.ElementTree(root)
设置文本值:element.text = ‘default’
设置属性:element.set(‘age’, str(i))
添加节点:root.append(element)
写入文档:tree.write(‘default.xml’, encoding=‘utf-8’, xml_declaration=True)

VOC数据集类别提取

提取VOC数据集中的特定类别;
思路:将符合需要提取的类别的坐标值等相关类容保存到另一个xml文件

import xml.etree.ElementTree as ET
import os
import shutil

"""
VOC类别提取:
1、读取文件
2、写入文件,
时间:2022.04.07
作者:余小晖 
"""

def __indent(elem, level=0):
    i = "\n" + level*"\t"
    if len(elem):
        if not elem.text or not elem.text.strip():
            elem.text = i + "\t"
        if not elem.tail or not elem.tail.strip():
            elem.tail = i
        for elem in elem:
            __indent(elem, level+1)
        if not elem.tail or not elem.tail.strip():
            elem.tail = i
    else:
        if level and (not elem.tail or not elem.tail.strip()):
            elem.tail = i


def VOC_extra(xml_path, img_path,xml_save_path, img_save_path, name_list, num=1):
    xmls = os.listdir(xml_path)
    for i, xml_file in enumerate(xmls):
        img_name = xml_file.split('.')[0] + '.jpg'  # 获取对应图片名
        tree = ET.parse(xml_path + xml_file)
        root = tree.getroot()
        # list_root = list(root)
        new_root = ET.Element('annotation')
        new_tree = ET.ElementTree(new_root)

        size = root.find('size')
        file_name = ET.Element('filename')
        file_name.text = img_name
        new_root.append(file_name)
        new_root.append(size)
        # names = root.findall('name')
        for obj in root.findall('object'):
            name = obj.find('name').text
            if name in name_list:
                new_root.append(obj)
        if len(new_root.findall('object')) > 0:
            __indent(new_root)
            new_tree.write(xml_save_path + xml_file, encoding='utf-8', xml_declaration=True)
            shutil.copy(img_path + img_name, img_save_path + img_name)
            print('num--------------------------', num)
            num += 1

if __name__ == '__main__':
    voc_classes = ["aeroplane", "bicycle", "bird", "boat", "bottle", "bus", "car", "cat",
               "chair", "cow", "diningtable", "dog", "horse", "motorbike", "person", "pottedplant",
               "sheep", "sofa", "train", "tvmonitor"]
    for name_list in voc_classes:
        file_save_name = name_list+ '_VOCtest2007'  #需要修改
        xml_path = './VOCtest_06-Nov-2007/VOCdevkit/VOC2007/Annotations/'   #改路径
        img_path = './VOCtest_06-Nov-2007/VOCdevkit/VOC2007/JPEGImages/'     #改路径
        xml_save_path = './VOCtest_06-Nov-2007/VOCdevkit/VOC2007/VOC_extra/' + file_save_name+ '/ann_xml/'   #改路径
        img_save_path = './VOCtest_06-Nov-2007/VOCdevkit/VOC2007/VOC_extra/'+ file_save_name+ '/images/'     #改路径
        if not os.path.exists(xml_save_path):
            os.makedirs(xml_save_path)
        if not os.path.exists(img_save_path):
            os.makedirs(img_save_path)
        # name_list = ['aeroplane']  #要提取的类别
        VOC_extra(xml_path, img_path,xml_save_path, img_save_path, name_list, num=1)

欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/langs/570007.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-04-09
下一篇 2022-04-09

发表评论

登录后才能评论

评论列表(0条)

保存