基于python标准库对XML文件的保存和加载
来源:互联网 发布:写日志的软件知乎 编辑:程序博客网 时间:2024/05/16 18:14
上文对基于PyQt对XML文件进行保存和加载进行说明,本文则是通过python标准库xml dom讲数据写入到xml文件然后解析,解析XML文件则通过两种方式:DOM和SAX。两者的区别是前者适合编辑文档结构,后者采用递归工作方式,适用于XML文档的搜索和处理。
下例通过XML DOM将不同类型的数据保存为XML格式如下:
<MOVIES VERSION="1.0"><MOVIE YEAR="1989" MINUTES="45" ACQUIRED="2017-01-15"><TITLE>God save world</TITLE><NOTES>HELLO WORLD</NOTES></MOVIE></MOVIES>
然后通过python标准库,DOM和SAX方式讲内容解析出来。
from xml.sax import *from xml.dom.minidom import Document,parseimport xml.dom.minidomimport osimport datetimeclass Movie(object): UNKNOWNYEAR = 1890 UNKNOWNMINUTES = 0 def __init__(self, title=None, year=UNKNOWNYEAR, minutes=UNKNOWNMINUTES, acquired=None, notes=None): self.title = title self.year = year self.minutes = minutes self.acquired = (acquired if acquired is not None else datetime.date.today()) self.notes = notesclass MovieContainer(object): def __init__(self,fname,movies): self.__fname = fname self.__movies = movies def exportXml(self, fname): try: doc = Document() movies = doc.createElement("MOVIES") movies.setAttribute("VERSION", "1.0") doc.appendChild(movies) movie=doc.createElement("MOVIE") movie.setAttribute("YEAR", str(self.__movies.year)) movie.setAttribute("MINUTES", str(self.__movies.minutes)) movie.setAttribute("ACQUIRED", str(self.__movies.acquired)) movies.appendChild(movie) title=doc.createElement("TITLE") title_value = doc.createTextNode(str(self.__movies.title)) title.appendChild(title_value) movie.appendChild(title) notes=doc.createElement("NOTES") notes_value = doc.createTextNode(str(self.__movies.notes)) notes.appendChild(notes_value) movie.appendChild(notes) # 将dom对象写入本地xml文件 with open(fname, 'wb') as f: f.write(doc.toprettyxml(indent='\t', newl="\n",encoding='utf-8')) except Exception as e: error = "Failed to export: {0}".format(e) print(error) else: print("Exported 1 movie records to {0}".format( os.path.basename(fname))) def importDOM(self, fname): try: # 使用minidom解析器打开 XML 文档 DOMTree = xml.dom.minidom.parse(fname) movies = DOMTree.documentElement # 在集合中获取所有电影 movie_c = movies.getElementsByTagName("MOVIE") for movie in movie_c: try: #print("*****Movie*****") if movie.hasAttribute("YEAR"): year=movie.getAttribute("YEAR") if movie.hasAttribute("MINUTES"): minutes=movie.getAttribute("MINUTES") if movie.hasAttribute("ACQUIRED"): ymd=movie.getAttribute("ACQUIRED").split("-") if len(ymd) != 3: raise ValueError("invalid acquired date {0}".format( str(movie.getAttribute("ACQUIRED")))) acquired = datetime.date(int(ymd[0]), int(ymd[1]), int(ymd[2])) title = notes = None title_tag = movie.getElementsByTagName('TITLE')[0] title=title_tag.childNodes[0].data notes_tag = movie.getElementsByTagName('NOTES')[0] try: notes=notes_tag.childNodes[0].data except Exception: raise ValueError("missing title or notes") except ValueError as e: print("Failed to import: {0}".format(e)) print(title,year,minutes,acquired,notes) except Exception as e: print(e) def importSAX_standard(self, fname): #try: # 创建一个 XMLReader parser = xml.sax.make_parser() # turn off namepsaces parser.setFeature(xml.sax.handler.feature_namespaces, 0) # 重写 ContextHandler Handler = MovieHandler(self.__movies) parser.setContentHandler(Handler) parser.parse(fname) print("Imported 1 movie records from {0}".format( os.path.basename(fname))) #except Exception as e: #print(e)class MovieHandler(ContentHandler): def __init__(self, movies): super(ContentHandler, self).__init__() self.CurrentData = "" self.movies = movies self.text = "" self.error = None def clear(self): self.year = None self.minutes = None self.acquired = None self.title = None self.notes = None def startElement(self, tag, attributes): #self.CurrentData = tag if tag == "MOVIE": self.clear() self.year = int(attributes["YEAR"]) self.minutes = int(attributes["MINUTES"]) ymd = attributes["ACQUIRED"].split("-") if len(ymd) != 3: raise ValueError("invalid acquired date {0}".format( str(attributes["ACQUIRED"]))) self.acquired = datetime.date(int(ymd[0]), int(ymd[1]), int(ymd[2])) elif tag in ("TITLE", "NOTES"): self.text = "" return True def characters(self, text): self.text += text return True def endElement(self, tag): if tag == "MOVIE": if (self.year is None or self.minutes is None or self.acquired is None or self.title is None or self.notes is None or not self.title): raise ValueError("incomplete movie record") print(self.title, self.year, self.minutes, self.acquired,self.notes) elif tag == "TITLE": self.title = self.text.strip() elif tag == "NOTES": self.notes = self.text.strip() return Trueif __name__ == "__main__": textdata=[["God save world",1989,45,None,"HELLO WORLD"]] fname="/home/yrd/work/movietest.xml" for data in textdata: movie=Movie(data[0],data[1],data[2],data[3],data[4]) moviecontainer=MovieContainer(fname, movie) print("#exportDOM") moviecontainer.exportXml(fname) print("#importDOM") moviecontainer.importDOM(fname) print("#importSAX") moviecontainer.importSAX_standard(fname)
运行结果;
exportDOM
Exported 1 movie records to movietest.xml
importDOM
God save world 1989 45 2017-01-15 HELLO WORLD
importSAX
God save world 1989 45 2017-01-15 HELLO WORLD
Imported 1 movie records from movietest.xml
0 0
- 基于python标准库对XML文件的保存和加载
- 基于PyQt5的XML文件的保存和加载
- Unity 保存和加载XML文件
- 对xml文件保存的代码改进
- python同时标准输出和重定向到文件保存
- 文件加载和保存
- 文件加载和保存
- ios的文件加载和保存
- Xml文件的保存
- CUJ:标准库:基于文件的容器
- 标准库:基于文件的容器
- XDocument 保存和加载XML文档
- spring基于xml加载和读取properties配置文件的方式
- java XML文件的保存
- MFC对文件读取和保存的操作
- Java对blob文件的保存和解析
- python解析基于xml格式的日志文件
- Python/Theano 加载和保存模型
- IOC和AOP
- 30 分钟学会 AWK
- http学习
- 2016年,我对爬虫的总结
- UITableViewCell重用
- 基于python标准库对XML文件的保存和加载
- 一个Linux下C线程池的实现(转)
- jzoj 1219 Num
- JavaScript将继承部分封装成函数extend
- 获取xmlString字符串中节点属性值
- Lucene全文搜索学习笔记(一)
- workbench出现there is not editable because there is no primary key
- 38
- 问题三十五: 怎么用ray tracing画二次曲面(quadratic surfaces)(2)——单页双曲面、双页双曲面、椭圆锥面、椭圆柱面