1. 什么是XML?
XML 指可扩展标记语言(eXtensible Markup Language),标准通用标记语言的子集,是一种用于标记电子文件使其具有结构性的标记语言。 XML 被设计用来传输和存储数据。XML是一套定义语义标记的规则,这些标记将文档分成许多部件并对这些部件加以标识。它也是元标记语言,即定义了用于定义其他与特定领域有关的、语义的、结构化的标记语言的句法语言。
python对XML的解析
常见的XML编程接口有DOM和SAX,这两种接口处理XML文件的方式不同,当然使用场合也不同。
python有三种方法解析XML,SAX,DOM,以及ElementTree:
- SAX (simple API for XML )
python 标准库包含SAX解析器,SAX用事件驱动模型,通过在解析XML的过程中触发一个个的事件并调用用户定义的回调函数来处理XML文件。 - DOM(Document Object Model)
将XML数据在内存中解析成一个树,通过对树的操作来操作XML。
下面用到的movies.xml内容:
<collection shelf="New Arrivals">
<movie title="Enemy Behind">
<type>War, Thriller</type>
<format>DVD</format>
<year>2003</year>
<rating>PG</rating>
<stars>10</stars>
<description>Talk about a US-Japan war</description>
</movie>
<movie title="Transformers">
<type>Anime, Science Fiction</type>
<format>DVD</format>
<year>1989</year>
<rating>R</rating>
<stars>8</stars>
<description>A schientific fiction</description>
</movie>
<movie title="Trigun">
<type>Anime, Action</type>
<format>DVD</format>
<episodes>4</episodes>
<rating>PG</rating>
<stars>10</stars>
<description>Vash the Stampede!</description>
</movie>
<movie title="Ishtar">
<type>Comedy</type>
<format>VHS</format>
<rating>PG</rating>
<stars>2</stars>
<description>Viewable boredom</description>
</movie>
</collection>
2. SAX解析xml
1). SAX是一种基于事件驱动的API。利用SAX解析XML文档牵涉到两个部分:解析器和事件处理器。解析器负责读取XML文档,并向事件处理器发送事件,如元素开始跟元素结束事件;而事件处理器则负责对事件作出相应,对传递的XML数据进行处理。
1、对大型文件进行处理;
2、只需要文件的部分内容,或者只需从文件中得到特定信息。
3、想建立自己的对象模型的时候。
2). 在python中使用sax方式处理xml要先引入xml.sax中的parse函数,还有xml.sax.handler中的ContentHandler。
ContentHandler类方法介绍
- characters(content)方法
调用时机:
1>. 从行开始,遇到标签之前,存在字符,content的值为这些字符串。
2>. 从一个标签,遇到下一个标签之前, 存在字符,content的值为这些字符串。
3>. 从一个标签,遇到行结束符之前,存在字符,content的值为这些字符串。
4>. 标签可以是开始标签,也可以是结束标签。 - startDocument()方法: 文档启动的时候调用。
- endDocument()方法: 解析器到达文档结尾时调用。
- startElement(name, attrs)方法: 遇到XML开始标签时调用,name是标签的名字,attrs是标签的属性值字典。
- endElement(name)方法: 遇到XML结束标签时调用。
3). make_parser方法
以下方法创建一个新的解析器对象并返回。
xml.sax.make_parser( [parser_list] )
参数说明:
parser_list - 可选参数,解析器列表
4). parser方法
以下方法创建一个 SAX 解析器并解析xml文档:
xml.sax.parse( xmlfile, contenthandler[, errorhandler])
参数说明:
xmlfile - xml文件名
contenthandler - 必须是一个ContentHandler的对象
errorhandler - 如果指定该参数,errorhandler必须是一个SAX ErrorHandler对象
5). parseString方法
parseString方法创建一个XML解析器并解析xml字符串:
xml.sax.parseString(xmlstring, contenthandler[, errorhandler])
参数说明:
xmlstring - xml字符串
contenthandler - 必须是一个ContentHandler的对象
errorhandler - 如果指定该参数,errorhandler必须是一个SAX ErrorHandler对象
6). 示例:
import xml.sax
class MovieHandler(xml.sax.ContentHandler):
"""docstring for MovieHandler"""
def __init__(self):
super(MovieHandler, self).__init__()
self.CurrendData = ""
self.type = ""
self.format = ""
self.year = ""
self.rating = ""
self.stars = ""
self.description = ""
# 元素开始调用
def startElement(self, tag, attributes):
self.CurrendData = tag
if tag == "movie":
print("******Movie******")
title = attributes["title"]
print("Title: ", title)
pass
pass
# 元素结束调用
def endElement(self, tag):
if self.CurrendData == "type":
print("Type: ", self.type)
elif self.CurrendData == "format":
print("Format: ", self.format)
elif self.CurrendData == "year":
print("Year: ", self.year)
elif self.CurrendData == "rating":
print("Rating: ", self.rating)
elif self.CurrendData == "stars":
print("Stars: ", self.stars)
elif self.CurrendData == "description":
print("Description: ", self.description)
self.CurrendData = ""
pass
# 读取字符时调用
def characters(self, content):
if self.CurrendData == "type":
self.type = content
elif self.CurrendData == "format":
self.format = content
elif self.CurrendData == "year":
self.year = content
elif self.CurrendData == "rating":
self.rating = content
elif self.CurrendData == "stars":
self.stars = content
elif self.CurrendData == "description":
self.description = content
pass
if (__name__ == "__main__") :
# 创建一个XMLReader
parser = xml.sax.make_parser()
# 关闭命名空间
parser.setFeature(xml.sax.handler.feature_namespaces, 0)
# 重写 ContextHandler
handler = MovieHandler()
parser.setContentHandler(handler)
parser.parse("movies.xml")
pass
打印结果:
3. Dom解析xml
文件对象模型(Document Object Model,简称DOM),是W3C组织推荐的处理可扩展置标语言的标准编程接口。一个 DOM 的解析器在解析一个 XML 文档时,一次性读取整个文档,把文档中所有元素保存在内存中的一个树结构里,之后你可以利用DOM 提供的不同的函数来读取或修改文档的内容和结构,也可以把修改过的内容写入xml文件。python中用xml.dom.minidom来解析xml文件.
示例:
from xml.dom.minidom import parse
import xml.dom.minidom
# 使用minidom解析器打开XML文档
DOMTree = xml.dom.minidom.parse("movies.xml")
# 获取collection节点
collection = DOMTree.documentElement
if collection.hasAttribute("shelf"):
print("Root element: %s" % collection.getAttribute("shelf"))
pass
# 在集合获取所有电影
movies = collection.getElementsByTagName("movie")
# 打印每部电影的详细信息
for movie in movies:
print("*******Movie********")
if movie.hasAttribute("title"):
print("Title: %s" % movie.getAttribute("title"))
pass
pass
type = movie.getElementsByTagName("type")[0]
print("Type: %s" % type.childNodes[0].data)
format = movie.getElementsByTagName("format")[0]
print("Format: %s" % format.childNodes[0].data)
rating = movie.getElementsByTagName("rating")[0]
print("Rating: %s" % rating.childNodes[0].data)
description = movie.getElementsByTagName("description")[0]
print("Description: %s" % description.childNodes[0].data)
打印结果:
4. JSON解析
JSON (JavaScript Object Notation) 是一种轻量级的数据交换格式。它基于ECMAScript的一个子集。
Python3 中可以使用 json 模块来对 JSON 数据进行编解码,它包含了两个函数:
- json.dumps(): 对数据进行编码。
- json.loads(): 对数据进行解码。
import json
# 字典
data = {
'no' : 1,
'name' : 'mazaiting',
'url' : 'https://www.jianshu.com/u/5d2cb4bfeb15'
}
# 将python字典类型装换为JSON对象
json_str = json.dumps(data)
print("Python 原始数据: ", repr(data))
print("JSON 对象: ", json_str)
# 将JSON对象转化为Python字典
data2 = json.loads(json_str)
print("data2['name']: ", data2['name'])
print("data2['url']: ", data2['url'])
打印结果:
5. 时间
Python 程序能用很多方式处理日期和时间,转换日期格式是一个常见的功能。Python 提供了一个 time 和 calendar 模块可以用于格式化日期和时间。时间间隔是以秒为单位的浮点小数。每个时间戳都以自从1970年1月1日午夜(历元)经过了多长时间来表示。Python 的 time 模块下有很多函数可以转换常见日期格式。如函数time.time()用于获取当前时间戳。
1). 获取当前时间戳
# 引入time模块
import time
ticks = time.time()
print("当前时间戳为:", ticks)
打印结果:
2). 时间元组
很多Python函数用一个元组装起来的9组数字处理时间:
序号 | 字段 | 值 |
---|---|---|
0 | 4位数年 | 2008 |
1 | 月 | 1 到 12 |
2 | 日 | 1到31 |
3 | 小时 | 0到23 |
4 | 分钟 | 0到59 |
5 | 秒 | 0到61 (60或61 是闰秒) |
6 | 一周的第几日 | 0到6 (0是周一) |
7 | 一年的第几日 | 1到366 (儒略历) |
8 | 夏令时 | -1, 0, 1, -1是决定是否为夏令时的旗帜 |
上述也就是struct_time元组。这种结构具有如下属性:
序号 | 属性 | 值 |
---|---|---|
0 | tm_year | 2008 |
1 | tm_mon | 1 到 12 |
2 | tm_mday | 1 到 31 |
3 | tm_hour | 0 到 23 |
4 | tm_min | 0 到 59 |
5 | tm_sec | 0 到 61 (60或61 是闰秒) |
6 | tm_wday | 0到6 (0是周一) |
7 | tm_yday | 一年中的第几天,1 到 366 |
8 | tm_isdst | 是否为夏令时,值有:1(夏令时)、0(不是夏令时)、-1(未知),默认 -1 |
3). 获取当前时间
从返回浮点数的时间辍方式向时间元组转换,只要将浮点数传递给如localtime之类的函数。
import time
localtime = time.localtime(time.time())
print("本地时间为:", localtime)
打印结果:
4). 获取格式化的时间
你可以根据需求选取各种格式,但是最简单的获取可读的时间模式的函数是asctime()
import time
localtime = time.asctime(time.localtime(time.time()))
print("本地时间为:", localtime)
打印结果:
5). 格式化日期
我们可以使用 time 模块的 strftime 方法来格式化日期:
time.strftime(format[, t])
示例:
import time
# 格式化成2016-03-20 11:45:39
print(time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()))
# 格式化成Wed Apr 11 16:56:32 2018形式
print(time.strftime("%a %b %d %H:%M:%S %Y", time.localtime()))
# 将格式字符串转换为时间戳
a = "Wed Apr 11 16:56:32 2018"
print(time.mktime(time.strptime(a, "%a %b %d %H:%M:%S %Y")))
打印结果:
6). python中时间日期格式化符号:
%y 两位数的年份表示(00-99)
%Y 四位数的年份表示(000-9999)
%m 月份(01-12)
%d 月内中的一天(0-31)
%H 24小时制小时数(0-23)
%I 12小时制小时数(01-12)
%M 分钟数(00=59)
%S 秒(00-59)
%a 本地简化星期名称
%A 本地完整星期名称
%b 本地简化的月份名称
%B 本地完整的月份名称
%c 本地相应的日期表示和时间表示
%j 年内的一天(001-366)
%p 本地A.M.或P.M.的等价符
%U 一年中的星期数(00-53)星期天为星期的开始
%w 星期(0-6),星期天为星期的开始
%W 一年中的星期数(00-53)星期一为星期的开始
%x 本地相应的日期表示
%X 本地相应的时间表示
%Z 当前时区的名称
%% %号本身
7). 日期
Calendar模块有很广泛的方法用来处理年历和月历.
# 获取某月日历
import calendar
cal = calendar.month(2018, 4)
print("以下输出2016年1月份的日历:")
print(cal)
打印结果: