python解析xml模块封装代码


Posted in Python onFebruary 07, 2014

有如下的xml文件:

<?xml version="1.0" encoding="utf-8" ?>  
<root>  
<childs>  
<child name='first' >1</child>  
<child value="2">2</child>  
</childs>  
</root>

下面介绍python解析xml文件的几种方法,使用python模块实现。

方式1,python模块实现自动遍历所有节点:

#!/usr/bin/env python  
# -*- coding: utf-8 -*-  
from xml.sax.handler import ContentHandler  
from xml.sax import parse
class TestHandle(ContentHandler):  
    def __init__(self, inlist):  
        self.inlist = inlist      def startElement(self,name,attrs):  
        print 'name:',name, 'attrs:',attrs.keys()  
    def endElement(self,name):  
        print 'endname',name  
    def characters(self,chars):  
        print 'chars',chars  
        self.inlist.append(chars)  
              
if __name__ == '__main__':  
    lt = []  
    parse('test.xml', TestHandle(lt))  
    print lt

结果:
[html] view plaincopy
name: root attrs: [] 
chars  

name: childs attrs: [] 
chars  

name: child attrs: [u'name'] 
chars 1 
endname child 
chars  

name: child attrs: [u'value'] 
chars 2 
endname child 
chars  

endname childs 
chars  

endname root 
[u'\n', u'\n', u'1', u'\n', u'2', u'\n', u'\n']

方式2,python模块实现获取根节点,按需查找指定节点:

#!/usr/bin/env python    
# -*- coding: utf-8 -*-    
from xml.dom import minidom    
xmlstr = '''''<?xml version="1.0" encoding="UTF-8"?> 
<hash> 
    <request name='first'>/2/photos/square/type.xml</request> 
    <error_code>21301</error_code> 
    <error>auth faild!</error> 
</hash> 
'''  
def doxml(xmlstr):  
    dom = minidom.parseString(xmlstr)      
    print 'Dom:'      
    print dom.toxml()        root = dom.firstChild      
    print 'root:'      
    print root.toxml()    
    childs = root.childNodes    
    for child in childs:  
        print child.toxml()  
        if child.nodeType == child.TEXT_NODE:  
            pass  
        else:  
            print 'child node attribute name:', child.getAttribute('name')  
            print 'child node name:', child.nodeName  
            print 'child node len:',len(child.childNodes)  
            print 'child data:',child.childNodes[0].data  
            print '======================================='  
            print 'more help info to see:'  
            for med in dir(child):  
                print help(med)      
                
if __name__ == '__main__':    
    doxml(xmlstr)

结果:
[html] view plaincopy
Dom: 
<?xml version="1.0" ?><hash> 
    <request name="first">/2/photos/square/type.xml</request> 
    <error_code>21301</error_code> 
    <error>auth faild!</error> 
</hash> 
root: 
<hash> 
    <request name="first">/2/photos/square/type.xml</request> 
    <error_code>21301</error_code> 
    <error>auth faild!</error> 
</hash> 

<request name="first">/2/photos/square/type.xml</request> 
child node attribute name: first 
child node name: request 
child node len: 1 
child data: /2/photos/square/type.xml 
======================================= 
more help info to see: 
两种方法各有其优点,python的xml处理模块太多,目前只用到这2个。

=====补充分割线================
实际工作中发现python的mimidom无法解析其它编码的xml,只能解析utf-8的编码,而其xml文件的头部申明也必须是utf-8,为其它编码会报错误。
网上的解决办法都是替换xml文件头部的编码申明,然后转换编码为utf-8再用minidom解码,实际测试为可行,不过有点累赘的感觉。

本节是 python解析xml模块封装代码 的第二部分。
====写xml内容的分割线=========

#!\urs\bin\env python  
#encoding: utf-8  
from xml.dom import minidom  class xmlwrite:  
    def __init__(self, resultfile):  
        self.resultfile = resultfile  
        self.rootname = 'api'  
        self.__create_xml_dom()  
    def __create_xml_dom(self):  
        xmlimpl = minidom.getDOMImplementation()  
        self.dom = xmlimpl.createDocument(None, self.rootname, None)  
        self.root = self.dom.documentElement  
    def __get_spec_node(self, xpath):  
        patharr = xpath.split(r'/')  
        parentnode = self.root  
        exist = 1  
        for nodename in patharr:  
            if nodename.strip() == '':  
                continue  
            if not exist:  
                return None  
            spcindex = nodename.find('[')  
            if spcindex > -1:  
                index = int(nodename[spcindex+1:-1])  
            else:  
                index = 0  
            count = 0  
            childs = parentnode.childNodes  
            for child in childs:  
                if child.nodeName == nodename[:spcindex]:  
                    if count == index:  
                        parentnode = child  
                        exist = 1  
                        break  
                    count += 1  
                    continue  
                else:  
                    exist = 0  
        return parentnode  
          
    def write_node(self, parent, nodename, value, attribute=None, CDATA=False):  
        node = self.dom.createElement(nodename)  
        if value:  
            if CDATA:  
                nodedata = self.dom.createCDATASection(value)  
            else:  
                nodedata = self.dom.createTextNode(value)  
            node.appendChild(nodedata)  
            if attribute and isinstance(attribute, dict):  
                for key, value in attribute.items():  
                    node.setAttribute(key, value)     
        try:  
            parentnode = self.__get_spec_node(parent)  
        except:  
            print 'Get parent Node Fail, Use the Root as parent Node'  
            parentnode = self.root  
        parentnode.appendChild(node)  
      
    def write_start_time(self, time):  
        self.write_node('/','StartTime', time)  
    def write_end_time(self, time):  
        self.write_node('/','EndTime', time)      
    def write_pass_count(self, count):  
        self.write_node('/','PassCount', count)     
    def write_fail_count(self, count):  
        self.write_node('/','FailCount', count)     
    def write_case(self):  
        self.write_node('/','Case', None)     
    def write_case_no(self, index, value):  
        self.write_node('/Case[%s]/' % index,'No', value)  
    def write_case_url(self, index, value):  
        self.write_node('/Case[%s]/' % index,'URL', value)  
    def write_case_dbdata(self, index, value):  
        self.write_node('/Case[%s]/' % index,'DBData', value)  
    def write_case_apidata(self, index, value):  
        self.write_node('/Case[%s]/' % index,'APIData', value)  
    def write_case_dbsql(self, index, value):  
        self.write_node('/Case[%s]/' % index,'DBSQL', value, CDATA=True)  
    def write_case_apixpath(self, index, value):  
        self.write_node('/Case[%s]/' % index,'APIXPath', value)         
    def save_xml(self):  
        myfile = file(self.resultfile, 'w')  
        self.dom.writexml(myfile, encoding='utf-8')  
        myfile.close()  
if __name__ == '__main__':  
      xr = xmlwrite(r'D:\test.xml')  
      xr.write_start_time('2223')  
      xr.write_end_time('444')        
      xr.write_pass_count('22')  
      xr.write_fail_count('33')    
      xr.write_case()  
      xr.write_case()  
      xr.write_case_no(0, '0')  
      xr.write_case_url(0, 'http://www.google.com')     
      xr.write_case_url(0, 'http://www.google.com')     
      xr.write_case_dbsql(0, 'select * from ')  
      xr.write_case_dbdata(0, 'dbtata')  
      xr.write_case_apixpath(0, '/xpath')  
      xr.write_case_apidata(0, 'apidata')  
      xr.write_case_no(1, '1')         
      xr.write_case_url(1, 'http://www.baidu.com')     
      xr.write_case_url(1, 'http://www.baidu.com')     
      xr.write_case_dbsql(1, 'select 1 from ')  
      xr.write_case_dbdata(1, 'dbtata1')  
      xr.write_case_apixpath(1, '/xpath1')  
      xr.write_case_apidata(1, 'apidata1')  
      xr.save_xml()

以上封装了minidom,支持通过xpath来写节点,不支持xpath带属性的匹配,但支持带索引的匹配。
比如:/root/child[1], 表示root的第2个child节点。

Python 相关文章推荐
Python实现发送与接收邮件的方法详解
Mar 28 Python
python3+dlib实现人脸识别和情绪分析
Apr 21 Python
Python实现按当前日期(年、月、日)创建多级目录的方法
Apr 26 Python
详解Python 函数如何重载?
Apr 23 Python
Python对ElasticSearch获取数据及操作
Apr 24 Python
python 实现将文件或文件夹用相对路径打包为 tar.gz 文件的方法
Jun 10 Python
我们为什么要减少Python中循环的使用
Jul 10 Python
解决python 找不到module的问题
Feb 12 Python
用Python开发app后端有优势吗
Jun 29 Python
opencv 图像礼帽和图像黑帽的实现
Jul 07 Python
python如何实现word批量转HTML
Sep 30 Python
python中mongodb包操作数据库
Apr 19 Python
python 解析XML python模块xml.dom解析xml实例代码
Feb 07 #Python
python合并文本文件示例
Feb 07 #Python
python实现哈希表
Feb 07 #Python
python处理cookie详解
Feb 07 #Python
urllib2自定义opener详解
Feb 07 #Python
python解析html开发库pyquery使用方法
Feb 07 #Python
python3.3实现乘法表示例
Feb 07 #Python
You might like
ftp类(myftp.php)
2006/10/09 PHP
php 模拟post_验证页面的返回状态(实例讲解)
2013/10/28 PHP
PHP命名空间(Namespace)简明教程
2014/06/11 PHP
ThinkPHP CURD方法之limit方法详解
2014/06/18 PHP
Laravel 5框架学习之环境与配置
2015/04/08 PHP
php无限级分类实现评论及回复功能
2019/02/18 PHP
php设计模式之职责链模式实例分析【星际争霸游戏案例】
2020/03/27 PHP
HTTP状态代码以及定义(解释)
2007/02/02 Javascript
use jscript with List Proxy Server Information
2007/06/11 Javascript
远离JS灾难css灾难之 js私有函数和css选择器作为容器
2011/12/11 Javascript
百度地图api应用标注地理位置信息(js版)
2013/02/01 Javascript
JQuery.Ajax之错误调试帮助信息介绍
2013/07/04 Javascript
jquery foreach使用示例
2013/09/12 Javascript
JS获取当前网址、主机地址项目根路径
2013/11/19 Javascript
js读取被点击次数的简单实例(从数据库中读取)
2014/03/07 Javascript
将页面table内容与样式另存成excel文件的方法
2015/08/05 Javascript
使用BootStrap实现标签切换原理解析
2017/03/14 Javascript
javascript+html5+css3自定义提示窗口
2017/06/21 Javascript
Sublime Text新建.vue模板并高亮(图文教程)
2017/10/26 Javascript
微信小程序使用字体图标的方法
2019/05/23 Javascript
详解vue-video-player使用心得(兼容m3u8)
2019/08/23 Javascript
js实现数字从零慢慢增加到指定数字示例
2019/11/07 Javascript
你准备好迎接vue3.0了吗
2020/04/28 Javascript
[03:05]DOTA2英雄基础教程 嗜血狂魔
2013/12/10 DOTA
[00:36]DOTA2上海特级锦标赛 Archon战队宣传片
2016/03/04 DOTA
[01:03:27]Optic vs VGJ.S 2018国际邀请赛小组赛BO2 第一场 8.17
2018/08/20 DOTA
python在windows命令行下输出彩色文字的方法
2015/03/19 Python
python下setuptools的安装详解及No module named setuptools的解决方法
2017/07/06 Python
linux环境下Django的安装配置详解
2019/07/22 Python
python help函数实例用法
2020/12/06 Python
幼儿园庆六一游园活动方案
2014/01/29 职场文书
小学毕业典礼演讲稿
2014/09/09 职场文书
专题民主生活会对照检查材料思想汇报
2014/09/29 职场文书
晋江市人民政府党组群众路线教育实践活动整改方案
2014/10/25 职场文书
党员反腐倡廉学习心得体会
2015/08/15 职场文书
mysql事务对效率的影响分析总结
2021/10/24 MySQL