zoukankan      html  css  js  c++  java
  • python模块之xml.etree.ElementTree

    Python有三种方法解析XML,SAX,DOM,以及ElementTree
    ###1.SAX (simple API for XML )
           pyhton 标准库包含SAX解析器,SAX是一种典型的极为快速的工具,在解析XML时,不会占用大量内存。
    但是这是基于回调机制的,因此在某些数据中,它会调用某些方法进行传递。这意味着必须为数据指定句柄,
    以维持自己的状态,这是非常困难的。


    ###2.DOM(Document Object Model)
           与SAX比较,DOM典型的缺点是比较慢,消耗更多的内存,因为DOM会将整个XML数读入内存中,并为树
    中的第一个节点建立一个对象。使用DOM的好处是你不需要对状态进行追踪,因为每一个节点都知道谁是它的
    父节点,谁是子节点。但是DOM用起来有些麻烦。


    ###3.ElementTree(元素树)
         ElementTree就像一个轻量级的DOM,具有方便友好的API。代码可用性好,速度快,消耗内存少,这里主要
    介绍ElementTree。

    一 基本知识 
    1、插入节点 
    Element.insert(index, element) 、Element(tag[, attrib][, **extra]) 、SubElement(parent, tag[, attrib[, **extra]]) 、Element.append(subelement) 
    2、删除节点 
    Element.remove(subelement) 删除一个节点、Element.clear()删除该节点下所有子节点 
    3、在节点中插入属性 
    Element.set(key, value)

    4、查找节点

    a) Element.getiterator   b) Element.getchildren   c) Element.find   d) Element.findall

    #!/usr/bin/python
    # -*- encoding: utf-8 -*-
    
    import os
    import sys
    import os.path
    import xml.etree.ElementTree as ET
    
    
    def read_xml(xmlFile, destDir):
        # print '==----------------=',ET.parse(xmlFile)
    
        # 加载XML文件(2种方法,一是加载指定字符串,二是加载指定文件)c:xml1.xml
        
        '''
        <?xml version="1.0" ?>
    	<root>
    	  <FILE_DIRECTORY NAME="ca002">
    	   <FILE_DIRECTORY NAME="RT_CA">
    		<FILE_NAME NAME="0000.obj">
    			<COFF_FILE_HEAD BEGIN="0" END="20">
    				  <Machine>X86</Machine>
    				  <NumberOfSections>2</NumberOfSections>
    				  <PointerToSymbolTable>21205</PointerToSymbolTable>
    				  <NumberOfSymbols>107</NumberOfSymbols>
    				  <SizeOfOptionalHeader>0</SizeOfOptionalHeader>
    				  <Characteristics>0</Characteristics>
    			  </COFF_FILE_HEAD>
    			<COFF_IMAGE_SECTIONS>
    				<COFF_IMAGE_SECTION INDEX="0">
    				  <Name>.rdata</Name>
    				  <SizeOfRawData>5064</SizeOfRawData>
    				  <PointerToRawData>100</PointerToRawData>
    				  <PointerToRelocations>0</PointerToRelocations>
    				  <PointerToLinenumbers>0</PointerToLinenumbers>
    				  <NumberOfRelocations>0</NumberOfRelocations>
    				  <NumberOfLinenumbers>0</NumberOfLinenumbers>
    				</COFF_IMAGE_SECTION>
    			</COFF_IMAGE_SECTIONS>
    		</FILE_NAME>
    	   </FILE_DIRECTORY>
    	  </FILE_DIRECTORY>
    	</root>
        :param xmlFile: 
        :param destDir: 
        :return: 
        '''
        
        tree = ET.parse(xmlFile)
        root = tree.getroot()
        # root = ET.fromstring(xmlContent)
        dir1_nodes = root.getchildren()
        # create dir1
        for dir1_node in dir1_nodes:
            dir1 = destDir + os.path.sep + dir1_node.attrib['NAME']
            # print dir1
            if os.path.exists(dir1) == False:
                os.mkdir(dir1)
                # create dir2
            dir2_nodes = dir1_node.getchildren()
            for dir2_node in dir2_nodes:
                dir2 = dir1 + os.path.sep + dir2_node.attrib['NAME']
                if os.path.exists(dir2) == False:
                    os.mkdir(dir2)
                    # create file
                dir3_nodes = dir2_node.getchildren()
                for dir3_node in dir3_nodes:
                    dir3 = dir2 + os.path.sep + dir3_node.attrib['NAME']
    
                    # 参数w 会新建或覆盖一个文件,
                    f = open(dir3, 'w')
                    # 遍历xml标签name=***.obj
                    prelen = 0
                    dir4_nodes = dir3_node.getchildren()
                    for dir4_node in dir4_nodes:
                        traversal(dir4_node, f, prelen)
                    f.close()
    
    
    def traversal(node, f, prelen):
        '''''recursively traversal the rest of xml's content'''
        length = node.getchildren()
        attrs = ''
        texts = ''
        if len(node.attrib) > 0:
            for key in node.attrib:
                attrs += str(key) + ":" + str(node.attrib[key]) + " "
            attrs = attrs[:-1]
            f.write('-' * prelen + node.tag + '(' + attrs + ')')
        else:
            f.write('-' * prelen + node.tag)
        if node.text != None:
            f.write(':' + node.text)
        f.write('
    ')
        if length != 0:
            nodes = node.getchildren()
            prelen += 4
            for node1 in nodes:
                traversal(node1, f, prelen)
    
    
    def parseXmls(filePath, destDir):
        '''''traversal xmls directory'''
        if os.path.isfile(filePath) and os.path.basename(filePath).endswith('.xml'):
            # print 'filePath===',filePath
            read_xml(filePath, destDir)
        else:
            for item in os.listdir(filePath):
                print item
                subpath = filePath + os.path.sep + item
                parseXmls(subpath, destDir)
    
    
    def main():
        "Main function."
        # input xml dir
        while True:
            dir = raw_input("input the dir:")
            if not os.path.exists(dir):
                print("you input dir is not existed!")
                continue
            else:
                break
                # create the dir of dest path that using to store the parsing xmls
        '''''destDir = os.path.split(dir)[0]+os.sep+time.strftime('%Y%m%d')
            if not os.path.exists(destDir):
                os.mkdir(destDir) '''
    
        destDir = os.path.split(dir)[0] + os.path.sep + os.path.basename(dir) + 'xml'
    
        if os.path.exists(destDir) == False:
            os.mkdir(destDir)
            # recall the function of parse the xmls
        parseXmls(dir, destDir)
    
    
    if __name__ == '__main__':
        main()
    

      

  • 相关阅读:
    电脑提示无法装入/加载SolidWorks DLL文件:sldshellutils如何解决
    vmware vpshere 安装完的必备工作
    建立AD域,修改密码后不重启生效命令
    VMware vSphere 6 Enterprise Plus 注册码
    VMware-viclient-all
    域控中将组策略应用到安全组
    Windows server 2003域控迁移到2012
    SecureCRT 基本设置
    linux之"server" directive is not allowed here in
    wordpress(二)wordpress环境迁移
  • 原文地址:https://www.cnblogs.com/dancesir/p/6915802.html
Copyright © 2011-2022 走看看