Python解析VOC数据标签文件
Posted 修炼之路
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Python解析VOC数据标签文件相关的知识,希望对你有一定的参考价值。
导读
在目标检测数据集中我们经常会使用到VOC格式的数据,这篇文章就向大家介绍一下如何来解析xml
标签文件的数据
xml数据
<annotation>
<folder>/root/datasets</folder>
<filename>/root/datasets/example/example.jpg</filename>
<source>
<database>Unknown</database>
<annotation>Unknown</annotation>
<image>Unknown</image>
</source>
<size>
<width>1080</width>
<height>1440</height>
<depth></depth>
</size>
<segmented>0</segmented>
<object>
<name>1</name>
<occluded>0</occluded>
<bndbox>
<xmin>767.78</xmin>
<ymin>65.87</ymin>
<xmax>792.08</xmax>
<ymax>102.33</ymax>
</bndbox>
</object>
<object>
<name>2</name>
<occluded>0</occluded>
<bndbox>
<xmin>378.89</xmin>
<ymin>546.77</ymin>
<xmax>403.19</xmax>
<ymax>583.23</ymax>
</bndbox>
</object>
</annotation>
解析xml数据
python的xml
库提供了几种不同的方法来解析xml文件,下面我们来介绍如何通过ElementTree
和minidom
来解析xml文件
使用ElementTree解析xml数据
通过ElementTree解析xml数据主要分为下面几个步骤:
- 使用
getroot
方法来获取xml的根节点信息 - 使用
find
方法来找到不需要遍历节点的信息 - 通过
iter
来编译包含多个相同节点的信息
import xml.etree.ElementTree as ET
def parse_xml(xml_path):
#读取xml文件
rf = open(xml_path,"r")
#开始解析xml文件
tree = ET.parse(rf)
#获取根节点信息
root = tree.getroot()
#获取图片的路径
img_path = root.find("filename").text
#获取图片的size节点的信息
size = root.find("size")
#获取图片的宽
img_width = size.find("width").text
#获取图片的高
img_height = size.find("height").text
#解析图片的box信息
#遍历object节点的信息
label_infos = []
for object in root.iter("object"):
#获取类别的名称
name = object.find("name").text
#获取标签的识别难度
occluded = object.find("occluded").text
#获取标签的box信息
bndbox = object.find("bndbox")
xmin = float(bndbox.find('xmin').text)
xmax = float(bndbox.find('xmax').text)
ymin = float(bndbox.find('ymin').text)
ymax = float(bndbox.find('ymax').text)
box = (xmin,xmax,ymin,ymax)
label_infos.append((name,occluded,box))
return label_infos,img_width,img_height
使用minidom来解析xml文件
使用minidom
来解析xml相对于ElementTree
来说要稍微复杂一点,minidom
主要通过getElementsByTagName
函数来寻找节点,然后再通过childNodes
来逐步解析xml文件,我将minidom
解析xml文件以及封装成了三个函数:
get_all_node
获取节点下面所有的子节点get_node_value
获取节点的值get_node_name
获取节点的名称
from xml.dom import minidom
def parse_xml_by_minidom(xml_path):
def get_node_name(node):
"""获取节点的名字
:param node:
:return:
"""
return node.nodeName
def get_node_value(node):
"""获取node的值
:param node:
:return:
"""
child_nodes = node.childNodes
return child_nodes[0].nodeValue
def get_all_node(node,node_list):
"""获取所有的节点
:param node:
:param node_list:
:return:
"""
for child_node in node.childNodes:
if isinstance(child_node,minidom.Element):
child_nodes = child_node.childNodes
if len(child_nodes) == 1:
node_list.append(child_node)
else:
get_all_node(child_node,node_list)
def get_all_child_value(node):
"""获取节点所有子节点信息
:param node:
:return:
"""
node_list = []
get_all_node(node,node_list)
node_info =
for node in node_list:
node_name = get_node_name(node)
node_value = get_node_value(node)
if node_value is not None:
node_info[node_name] = node_value
return node_info
doc = minidom.parse(xml_path)
#获取跟节点
root = doc.documentElement
#获取图片的路径
img_path_node = root.getElementsByTagName("filename")[0]
#获取节点的名称
node_name = get_node_name(img_path_node)
#获取节点的值
img_path = get_node_value(img_path_node)
size_node_list = root.getElementsByTagName("size")
size_info = get_all_child_value(size_node_list[0])
#获取图片的宽和高
img_width = size_info["width"]
img_height = size_info["height"]
#获取标签信息
box_info_list = []
object_node_list = root.getElementsByTagName("object")
for object_node in object_node_list[:1]:
box_node_info = get_all_child_value(object_node)
box_info_list.append(box_node_info)
return box_info_list,img_width,img_height
以上是关于Python解析VOC数据标签文件的主要内容,如果未能解决你的问题,请参考以下文章
python [xml文件到voc的csv文件]将voc标签转换为xml格式为csv格式#python #csv #xml
labelimg标注的VOC格式标签xml文件和yolo格式标签txt文件相互转换
YOLO-Darknet实战:VOC2007标签格式转换成Darknet标签格式