【问题标题】:Scrape XML file with Python使用 Python 抓取 XML 文件
【发布时间】:2018-11-23 22:48:15
【问题描述】:

我一直在尝试抓取 XML 文件以从 2 个标签(仅代码和源代码)中复制内容。 xml 文件如下所示:

<Series xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
  <RunDate>2018-06-12</RunDate>
  <Instruments>
    <Instrument>
      <Code>27BA1</Code>
      <Source>YYY</Source>
    </Instrument>
    <Instrument>
      <Code>28BA1</Code>
      <Source>XXX</Source>
    </Instrument>
      <Code>29BA1</Code>
      <Source>XXX</Source>
    </Instrument>
      <Code>30BA1</Code>
      <Source>DDD</Source>
    </Instrument>
  </Instruments>
</Series>

我只是正确地抓取了第一个代码。下面是代码。有人可以帮忙吗?

import xml.etree.ElementTree as ET
import csv

tree = ET.parse("data.xml")
csv_fname = "data.csv"
root = tree.getroot()

f = open(csv_fname, 'w')
csvwriter = csv.writer(f)
count = 0
head = ['Code', 'Source']

csvwriter.writerow(head)

for time in root.findall('Instruments'):
    row = []
    job_name = time.find('Instrument').find('Code').text
    row.append(job_name)
    job_name_1 = time.find('Instrument').find('Source').text
    row.append(job_name_1)
    csvwriter.writerow(row)
f.close()

【问题讨论】:

    标签: python xml csv parsing


    【解决方案1】:

    您在帖子中提供的 XML 文件无效。 通过在此处粘贴文件进行检查。 https://www.w3schools.com/xml/xml_validator.asp

    我假设的有效 xml 是

    <Series xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
      <RunDate>2018-06-12</RunDate>
      <Instruments>
        <Instrument>
          <Code>27BA1</Code>
          <Source>YYY</Source>
        </Instrument>
        <Instrument>
          <Code>28BA1</Code>
          <Source>XXX</Source>
        </Instrument>
        <Instrument>
          <Code>29BA1</Code>
          <Source>XXX</Source>
        </Instrument>
        <Instrument>
          <Code>30BA1</Code>
          <Source>DDD</Source>
        </Instrument>
      </Instruments>
    </Series>
    

    打印代码和源标签中的值。

    from lxml import etree
    root = etree.parse('data.xml').getroot()
    instruments = root.find('Instruments')
    instrument = instruments.findall('Instrument')
    for grandchild in instrument:
        code, source = grandchild.find('Code'), grandchild.find('Source')
        print (code.text), (source.text)
    

    【讨论】:

      【解决方案2】:

      如果您能够对您的文档运行 xslt - 我假设您可以 - 一种替代方法将使这变得非常简单:

      <?xml version="1.0" encoding="utf-8"?>
      <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
          xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
      >
        <xsl:output method="text"/>
      
        <xsl:template match="/">
          <xsl:text>Code,Source</xsl:text><xsl:text>&#xa;</xsl:text>
          <xsl:apply-templates select="//Instrument"/>
        </xsl:template>
        <xsl:template match="Instrument">
      <xsl:value-of select="Code"/>,<xsl:value-of select="Source"/><xsl:text>&#xa;</xsl:text>
      </xsl:template>
      </xsl:stylesheet>
      

      注意&lt;xsl:text&gt;&amp;#xa;&lt;/xsl:text&gt; 元素的存在 - 这是为了插入在 CSV 中语义上重要但在 XML 中不重要的换行符。

      输出:

      Code,Source
      27BA1,YYY
      28BA1,XXX
      29BA1,XXX
      30BA1,DDD
      

      要在 Python 中运行它,我想您需要类似于this question 中建议的方法:

      import lxml.etree as ET
      
      dom = ET.parse(xml_filename)
      xslt = ET.parse(xsl_filename)
      transform = ET.XSLT(xslt)
      newdom = transform(dom)
      print(ET.tostring(newdom, pretty_print=True))
      

      我不使用 Python,所以我不知道这是否正确。

      糟糕 - 我也忽略了您的 XML 文档无效 - 第 11 行和第 14 行缺少打开的 &lt;Instrument&gt; 元素。在它们所属的位置添加这些元素可以正确转换文档。

      【讨论】:

      • 嗨。我不知道该怎么做。任何指导将不胜感激。谢谢
      • 您没有指定任何有关您使用的语言或环境的信息。我不认识你问题中的语言 - 所以通过扩展我也不知道你用什么来执行它。针对文档运行样式表的最佳方式取决于您的工具 - 请在问题中指定。谢谢。
      • 我认为这不是我想要的。我只是在找人 [租借看看我的 Python 代码并告诉我我做错了什么。不想使用 xslt。感谢您的帮助。
      猜你喜欢
      • 1970-01-01
      • 2012-02-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-07-20
      相关资源
      最近更新 更多