python - 在 python 中解析和转换嵌套 xml

标签 python xml pandas

我有以下 xml 数据。

<transaction>
        <date>20190415</date>
        <ticket>303434037</ticket>
        <value>15</value>
        <notenders>01</notenders>
        <tenderdetail>
            <tendertype>00</tendertype>
            <tenderamt>15</tenderamt>
        </tenderdetail>
        <item>
            <receipeno>00001096</receipeno>
            <price>7</price>
            <qty>0001</qty>
            <items>
                <item>
                    <receipeno>00000786</receipeno>
                    <price>8</price>
                    <qty>0001</qty>
                    <items>
                        <item>
                            <receipeno>00000599</receipeno>
                            <price>0</price>
                            <qty>1</qty>
                        </item>
                        <item>
                            <receipeno>00000605</receipeno>
                            <price>0</price>
                            <qty>1</qty>
                        </item>
                        <item>
                            <receipeno>00000608</receipeno>
                            <price>0</price>
                            <qty>0004</qty>
                        </item>
                    </items>
                </item>
                <item>
                    <receipeno>10000043</receipeno>
                    <price>0</price>
                    <qty>0001</qty>
                </item>
                <item>
                    <receipeno>00000381</receipeno>
                    <price>7</price>
                    <qty>0001</qty>
                    <items>
                    <item>
                            <receipeno>00000607</receipeno>
                            <price>0</price>
                            <qty>1</qty>
                        </item>
                    </items>
                </item>
            </items>
        </item>
   </transaction>

我需要将其转换为表格格式。问题是每个标签内有许多嵌套分支。例如很多<item> & <items>标签。与嵌套性无关。我需要将数据逐一列出。

我想要的输出如下

 +----------+--------+-------+-----------+------------+-----------+-----------+-------+-----+
|   date   | ticket | value | notenders | tendertype | tenderamt | receipeno | price | qty |
+----------+--------+-------+-----------+------------+-----------+-----------+-------+-----+
| 20190101 |  12345 |    15 |         1 |          0 |        15 |      1096 |     7 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       786 |     8 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       599 |     0 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       605 |     0 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       608 |     0 |   4 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       143 |     0 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       381 |     7 |   1 |
| 20190101 |  12345 |    15 |         1 |          0 |        15 |       607 |     0 |   1 |
+----------+--------+-------+-----------+------------+-----------+-----------+-------+-----+

我是 python 和 XML 解析新手。因此,请指导我解决这个问题。 ...

最佳答案

从必要的导入开始:

import pandas as pd
import xml.etree.ElementTree as et
import re

然后,要从要读取的标签中删除前导零,请定义以下函数:

def stripLZ(src):
    return re.sub(r'^0+(?=\d)', '', src)

要读取源文件及其根元素,请执行:

tree = et.parse('transaction.xml')
root = tree.getroot()

要从root级别读取标签(除了从item读取),请执行:

dt = root.find('date').text
tck = root.find('ticket').text
val = root.find('value').text
notend = stripLZ(root.find('notenders').text)

剩下的两个标签是下一级的,所以从读取它们的父标签开始:

tdet = root.find('tenderdetail')

并从中读取这些标签:

tendtyp = stripLZ(tdet.find('tendertype').text)
tendamt = tdet.find('tenderamt').text

请注意,我在这里使用了stripLZ函数(它将被使用 多几次)。

现在有时间创建结果 DataFrame:

df_cols = ['date', 'ticket', 'value', 'notenders',
    'tendertype', 'tenderamt', 'receipeno', 'price', 'qty']
df = pd.DataFrame(columns = df_cols)

并且可以使用iter方法执行加载循环:

for it in root.iter('item'):
    rcp = it.find('receipeno').text
    prc = it.find('price').text
    qty = stripLZ(it.find('qty').text)
    df = df.append(pd.Series([dt, tck, val, notend,
        tendtyp, tendamt, rcp, prc, qty],
        index = df_cols), ignore_index=True)

这个循环:

  • 迭代所有 item 标签,无论其深度如何。
  • 从当前项目读取 3 个标签。
  • 将一行附加到结果 DataFrame。

关于python - 在 python 中解析和转换嵌套 xml,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56406117/

相关文章:

python - 具有 bool 值和整数的数据框的 Pandas 条件子集

javascript - 在浏览器中修改XML文档

Python:将不同文件夹中的相同 .csv 文件(每个文件夹都有一个 .csv 文件)复制到一个文件夹中

xml - 孙元素的XPath测试值?

javascript - 在nodejs或Javascript中完成空XML标签?

python - Pandas Dataframe 按列分组

python - 使用 Pandas groupby 数据帧中的第一行计算累积差异

python - 如何使用 Consul Agent CLI 创建新的 KV 条目,但前提是它们尚不存在?

python - 为什么 python-selenium-webdriver 'quit' 不退出?

python - 如何在 python3 中的慢速测试中提前失败(例如设置超时)(最好使用nose)