这篇文章将为大家详细讲解有关python如何实现xml解析,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。
三种方法:一是.dom.*模块,它是w3c dom api的实现,若需要处理dom api则该模块很适合;二是xml.sax.*模块,它是sax api的实现,这个模块牺牲了便捷性来换取速度和内存占用,sax是一个基于事件的api,这就意味着它可以“在空中”处理庞大数量的的文档,不用完全加载进内存;三是xml.etree.elementtree模块(简称 et),它提供了轻量级的python式的api,相对于dom来说et 快了很多,而且有很多令人愉悦的api可以使用,相对于sax来说et的et.iterparse也提供了 “在空中” 的处理方式,没有必要加载整个文档到内存,et的性能的平均值和sax差不多,但是api的效率更高一点而且使用起来很方便。
1、dom(document object model)
一个 dom 的解析器在解析一个 xml 文档时,一次性读取整个文档,把文档中所有元素保存在内存中的一个树结构里,之后你可以利用dom 提供的不同的函数来读取或修改文档的内容和结构,也可以把修改过的内容写入xml文件。
python中用xml.dom.minidom来解析xml文件。
本文使用的示例文件movie.xml内容如下
war, thriller dvd 2003 pg 10 talk about a us-japan war anime, science fiction dvd 1989 r 8 a schientific fiction anime, action dvd 4 pg 10 vash the stampede! comedy vhs pg 2 viewable boredom
python实现如下
# !/usr/bin/python # -*- coding: utf-8 -*- from xml.dom.minidom import parse import xml.dom.minidom # 使用minidom解析器打开 xml 文档 domtree = xml.dom.minidom.parse("movie.xml") #得到元素对象 collection = domtree.documentelement if collection.hasattribute("shelf"): print("root element : %s" % collection.getattribute("shelf")) #获取标签名 #print(collection.nodename) # 在集合中获取所有电影 movies = collection.getelementsbytagname("movie") # 打印每部电影的详细信息 for movie in movies: print("*****movie*****") if movie.hasattribute("title"): print("title: %s" % movie.getattribute("title")) type = movie.getelementsbytagname('type')[0] print("type: %s" % type.childnodes[0].data) format = movie.getelementsbytagname('format')[0] print("format: %s" % format.childnodes[0].data) year=movie.getelementsbytagname("year") if len(year)>0: print("year: %s" % year[0].firstchild.data) #父节点 parentnode #print(year[0].parentnode.nodename) rating = movie.getelementsbytagname('rating')[0] print("rating: %s" % rating.childnodes[0].data) description = movie.getelementsbytagname('description')[0] # 显示标签对之间的数据 print("description: %s" % description.childnodes[0].data) #print("description: %s" % description.firstchild.data)
执行结果:
root element : new arrivals *****movie***** title: enemy behind type: war, thriller format: dvd year: 2003 rating: pg description: talk about a us-japan war *****movie***** title: transformers type: anime, science fiction format: dvd year: 1989 rating: r description: a schientific fiction *****movie***** title: trigun type: anime, action format: dvd rating: pg description: vash the stampede! *****movie***** title: ishtar type: comedy format: vhs rating: pg description: viewable boredom
2、elementtree(元素树)
elementtree就像一个轻量级的dom,具有方便友好的api。代码可用性好,速度快,消耗内存少。
在python中,解析xml文件时,会选用elementtree或者celementtree,那么两者有什么不同呢?
1、celementtree速度上要比elementtree快,比较celementtree是用c语音写的;
2、debug调试的时候,celementtree是看不到解析的字段内容的,所以不适合用于调试的情况,而elementtree可以看到解析的内容,方便调试时取值
3、在用到iter,迭代取某个标签时,celementtree不能用,因为它没有这个函数,而elementtree有这个函数;当然可能还有其他函数的差异
所有平时,我们一般这么用,比较速度快吗。调试的时候使用elementtree。遇到某些特别的函数,只能选择拥有这个函数的使用
try:
import xml.etree.celementtree as et
except:
import xml.etree.elementtree as et
从python3.3开始elementtree模块会自动寻找可用的c库来加快速度
import xml.etree.elementtree as et import sys import os.path def traversexml(element): #print (len(element)) if len(element) > 0: for child in element: print("********movie********") print("title:",child.get("title")) for childchild in child: print(childchild.tag,":",childchild.text) #traversexml(child) #else: # print (element.tag, "----", element.attrib) def readxml(xmlfile): try: tree = et.parse(xmlfile) #print("tree type:", type(tree)) # 获得根节点 root = tree.getroot() except exception as e: # 捕获除与程序退出sys.exit()相关之外的所有异常 print("parse ***.xml fail!") sys.exit() #print("root type:", type(root)) #root.attrib访问root属性,root.tag标签 #print(root.tag, ":", root.attrib) return root if __name__ == "__main__": xmlfilepath = os.path.abspath("movie.xml") root=readxml(xmlfilepath) # # 使用下标访问 # print(root[0][0].text) # print(root[1][2].text) #根据标签名查找root下的所有标签 # movies=root.findall("movie") #遍历子标签 # print(len(movies)) # for movie in movies: # type=movie.find("type") # print(type.text) # 遍历xml文件 traversexml(root)
3、sax (simple api for xml )
python 标准库包含 sax 解析器,sax 用事件驱动模型,通过在解析xml的过程中触发一个个的事件并调用用户定义的回调函数来处理xml文件。
sax是一种基于事件驱动的 api。
利用sax解析xml文档牵涉到两个部分: 解析器和事件处理器。
解析器负责读取xml文档,并向事件处理器发送事件,如元素开始跟元素结束事件。
而事件处理器则负责对事件作出响应,对传递的xml数据进行处理。
-
1、对大型文件进行处理;
-
2、只需要文件的部分内容,或者只需从文件中得到特定信息。
-
3、想建立自己的对象模型的时候。
在python中使用sax方式处理xml要先引入xml.sax中的parse函数,还有xml.sax.handler中的contenthandler。
contenthandler类方法介绍
characters(content)方法
调用时机:
从行开始,遇到标签之前,存在字符,content 的值为这些字符串。
从一个标签,遇到下一个标签之前, 存在字符,content 的值为这些字符串。
从一个标签,遇到行结束符之前,存在字符,content 的值为这些字符串。
标签可以是开始标签,也可以是结束标签。
startdocument() 方法
文档启动的时候调用。
enddocument() 方法
解析器到达文档结尾时调用。
startelement(name, attrs)方法
遇到xml开始标签时调用,name是标签的名字,attrs是标签的属性值字典。
endelement(name) 方法
遇到xml结束标签时调用。
#!/usr/bin/python # -*- coding: utf-8 -*- import xml.sax class moviehandler(xml.sax.contenthandler): def __init__(self): self.currentdata = "" self.type = "" self.format = "" self.year = "" self.rating = "" self.stars = "" self.description = "" # 元素开始事件处理 def startelement(self, tag, attributes): self.currentdata = tag if tag == "movie": print("*****movie*****") title = attributes["title"] print("title:", title) # 元素结束事件处理 def endelement(self, tag): if self.currentdata == "type": print("type:", self.type) elif self.currentdata == "format": print("format:", self.format) elif self.currentdata == "year": print("year:", self.year) elif self.currentdata == "rating": print("rating:", self.rating) elif self.currentdata == "stars": print("stars:", self.stars) elif self.currentdata == "description": print("description:", self.description) self.currentdata = "" # 内容事件处理 def characters(self, content): if self.currentdata == "type": self.type = content elif self.currentdata == "format": self.format = content elif self.currentdata == "year": self.year = content elif self.currentdata == "rating": self.rating = content elif self.currentdata == "stars": self.stars = content elif self.currentdata == "description": self.description = content if (__name__ == "__main__"): # 创建一个 xmlreader parser = xml.sax.make_parser() # turn off namepsaces parser.setfeature(xml.sax.handler.feature_namespaces, 0) # 重写 contexthandler handler = moviehandler() parser.setcontenthandler(handler) parser.parse("movie.xml")
关于“python如何实现xml解析”这篇文章就分享到这里了,希望以上内容可以对大家有一定的帮助,使各位可以学到更多知识,如果觉得文章不错,请把它分享出去让更多的人看到。