python中的xml到csv转换

时间:2017-08-03 05:49:07

标签: python xml csv

这里我需要解析xml并获取值。我需要得到属性元素,例如' personid = 01'这是我无法得到的代码。而且我还需要获取grand children节点值。这是为了#S; SIBLING"和它的名称tags.BUt我不能硬编码为兄弟和获取值。最重要的是,我需要处理多个属性并加入它们以形成一个唯一的键,它将作为最终表中的一列。

import xml.dom
import xml.dom.minidom

doc = xml.dom.minidom.parseString('''
<root>
   <person id="01"> 
      <name> abc</name> 
      <age>32</age>
      <address>addr123</address>
      <siblings>
        <name></name>
      </siblings>
   </person>
   <person id="02">
      <name> def</name>
      <age>22</age>
      <address>addr456</address>
      <siblings>
        <name></name>
        <name></name>
      </siblings>
   </person>
</root>

''')

innerlist=[]
outerlist=[]
def innerHtml(root):
    text = '' 
    nodes = [ root ]
    while not nodes==[]:
        node = nodes.pop()
        if node.nodeType==xml.dom.Node.TEXT_NODE:
            text += node.wholeText
        else:
            nodes.extend(node.childNodes)
    return text

for statusNode in doc.getElementsByTagName('person'):
    for childNode in statusNode.childNodes:
        if childNode.nodeType==xml.dom.Node.ELEMENT_NODE:
           if innerHtml(childNode).strip() != '':
              innerlist.append(childNode.nodeName+" "+innerHtml(childNode).strip())
    outerlist.append(innerlist)
    innerlist=[]
#print(outerlist) 

attrlist = []
nodes = doc.getElementsByTagName('person')
for node in nodes:
    if 'id' in node.attributes:
        #print(node.attributes['id'].value)
        attrlist.append(node.attributes['id'].value)
#print(attrlist)

dictionary = dict(zip(attrlist, outerlist))
print(dictionary) 

1 个答案:

答案 0 :(得分:0)

  

评论:我已将其存储在dictnorary中。 {'01': ['name abc', 'age 32', 'address addr123'], '02': ['name def', 'age 22', 'address addr456']}

您不能将dict写入CSV!

ValueError: dict contains fields not in fieldnames: '01' 

REALY 是否要转换为 CSV
阅读CSV File Reading and Writing

  

评论:这里我需要将sibiling标签作为另一个内部列表。

CSV不支持此 内部列表
编辑您的问题并显示预期的CSV输出!

  

问题:xml到csv转换

xml.etree.ElementTree的解决方案。

  

注意:不明白您希望如何处理 大孩子节点值
  将其作为dict的列表写在一列中。

import csv
import xml.etree.ElementTree as ET
root = ET.fromstring(doc)

fieldnames = None
with open('doc.csv', 'w') as fh:
    for p in root.findall('person'):
        person = {'_id':p.attrib['id']}
        for element in p:
            if len(element) >= 1:
                person[element.tag] = []
                for sub_e in element:
                    person[element.tag].append({sub_e.tag:sub_e.text})
            else:
                person[element.tag] = element.text

        if not fieldnames:
            fieldnames = sorted(person)
            w = csv.DictWriter(fh, fieldnames=fieldnames)
            w.writeheader()

        w.writerow(person)
  

<强>输出

_id,address,age,name,siblings
01,addr123,32, abc,[{'name': 'sib1'}]
02,addr456,, def,"[{'name': 'sib2'}, {'name': 'sib3'}]"

使用Python测试:3.4.2