Python条件XML编写

时间:2012-10-25 16:09:25

标签: python xml

我使用Python将CSV文件转换为XML格式。 CSV文件具有不同的行数,范围从2(包括标题)到无穷大。 (实际上10-15但除非有一些主要的性能问题,我想覆盖我的基础)为了转换文件,我有以下代码:

for row in csvData:
    if rowNum == 0:
        xmlData.write('    <'+csvFile[:-4]+'-1>' + "\n")
        tags = row
        # replace spaces w/ underscores in tag names
        for i in range(len(tags)):
            tags[i] = tags[i].replace(' ', '_')
    if rowNum == 1: 
        for i in range(len(tags)):
            xmlData.write('        ' + '<' + tags[i] + '>' \
                          + row[i] + '</' + tags[i] + '>' + "\n")
        xmlData.write('    </'+csvFile[:-4]+'-1>' + "\n" + '    <' +csvFile[:-4]+'-2>' + "\n")
    if rowNum == 2:
        for i in range(len(tags)):
            xmlData.write('        ' + '<' + tags[i] + '>' \
                          + row[i] + '</' + tags[i] + '>' + "\n")
        xmlData.write('    </'+csvFile[:-4]+'-2>' + "\n")
    if rowNum == 3:
        for i in range(len(tags)):
            xmlData.write('<'+csvFile[:-4]+'-3>' + "\n" + '        ' + '<' + tags[i] + '>' \
                          + row[i] + '</' + tags[i] + '>' + "\n")
        xmlData.write('    </'+csvFile[:-4]+'-3>' + "\n")

    rowNum +=1
xmlData.write('</csv_data>' + "\n")
xmlData.close()

如您所见,如果行存在,我将手动创建上层标记。有没有更有效的方法来实现我创建<csvFile-*></csvFile-*>标记的目标,而不是重复我的代码15次?谢谢!

1 个答案:

答案 0 :(得分:4)

我会使用xml.etree.ElementTreelxml.etree来编写XML。 xml.etree.ElementTree在标准库中,但没有内置的漂亮打印。 (您可以使用here中的缩进功能。)

lxml.etree是第三方模块,但它的tostring方法内置了漂亮的打印功能。

使用lxml.etree,你可以这样做:

import lxml.etree as ET

csvData = [['foo bar', 'baz quux'],['bing bang', 'bim bop', 'bip burp'],]
csvFile = 'rowboat'
name = csvFile[:-4]
root = ET.Element('csv_data')
for num, tags in enumerate(csvData):
    row = ET.SubElement(root, '{f}-{n}'.format(f = name, n = num))
    for text in tags:
        text = text.replace(' ', '_')
        tag = ET.SubElement(row, text)
        tag.text = text

print(ET.tostring(root, pretty_print = True))

产量

<csv_data>
  <row-0>
    <foo_bar>foo_bar</foo_bar>
    <baz_quux>baz_quux</baz_quux>
  </row-0>
  <row-1>
    <bing_bang>bing_bang</bing_bang>
    <bim_bop>bim_bop</bim_bop>
    <bip_burp>bip_burp</bip_burp>
  </row-1>
</csv_data>

一些建议:

  • 在Python中,几乎从不需要说

    for i in range(len(tags)):
        # do stuff with tags[i]
    

    相反说

    for tag in tags:
    

    循环遍历tags中的所有项目。

  • 而不是通过

    循环手动计算时间
    num = 0
    for tags in csvData:
        num += 1
    

    而是使用enumerate函数:

    for num, tags in enumerate(csvData):
    
  • 这样的字符串
    '        ' + '<' + tags[i] + '>' \
                             + row[i] + '</' + tags[i] + '>' + "\n"
    

    非常难以阅读。它混合了逻辑 缩进,使用标记的XML语法,使用end的minutia 行字符。这就是xml.etree.ElementTreelxml.etree的位置 会帮助你。它将负责XML的序列化 您;您需要提供的只是XML元素之间的关系。 代码将更易读,更易于维护。