【问题标题】:Modify xml values file using python [closed]使用python修改xml值文件[关闭]
【发布时间】:2013-01-29 04:21:11
【问题描述】:

我对python很陌生,我需要修改

<test name="test02"></xmpp> to <test name="test03"></xmpp> 

<temp-config>QA</temp-config> to <temp-config>Prod</temp-config> 

使用 python 的所有 5 次出现。 不确定要使用什么库。非常感谢您提供任何帮助。

<config>
<logging></logging>
<test-mode>false</test-mode>
<test name="test02"></xmpp>
<mail></mail>
<test-system>0</test-system>
<system id="0" name="suite1" type="regression">
    <temp-config>QA</temp-config>
    <rpm>0.5</rpm>
    <cycles>3</cycles>
</system>
<system id="1" name="suite2" type="regression">
    <temp-config>QA</temp-config>
    <rpm>0.5</rpm>
    <cycles>3</cycles>
</system>
<system id="2" name="suite3" type="regression">
    <temp-config>QA</temp-config>
    <rpm>0.5</rpm>
    <cycles>3</cycles>
</system>
<system id="3" name="suite4" type="regression">
    <temp-config>QA</temp-config>
    <rpm>0.5</rpm>
    <cycles>3</cycles>
</system>
<system id="4" name="suite5" type="regression">
    <temp-config>QA</temp-config>
    <rpm>0.5</rpm>
    <cycles>3</cycles>
</system>
</config>

【问题讨论】:

    标签: python xml parsing


    【解决方案1】:

    使用lxml。此示例使用 lxml.etree 并且实际上会在您的示例 xml 上失​​败,因为其中包含一些未关闭的标签。如果您对要解析的真实数据有同样的问题,请使用可以处理损坏的 xml 的lxml.html,作为 cmets 添加到代码中的指令)。

    In [14]: import lxml.etree as et  # for broken xml add an import:
                                      # import lxml.html as lh
    
    In [15]: doc = et.fromstring(xmlstr)  # for broken xml replace this line with:
                                          # doc = lh.fromstring(xmlstr)
    
                                          # if you read xml from a file:
                                          # doc = et.parse('file_path')
    
    In [16]: for elem in doc.xpath('.//temp-config'):
        ...:     elem.text = 'Prod'
        ...:     
    
    In [17]: print et.tostring(doc,pretty_print=True)
    <config>
      <logging/>
      <test-mode>false</test-mode>
      <test name="test02">
        <mail/>
        <test-system>0</test-system>
        <system id="0" name="suite1" type="regression">
          <temp-config>Prod</temp-config>
          <rpm>0.5</rpm>
          <cycles>3</cycles>
        </system>
        <system id="1" name="suite2" type="regression">
          <temp-config>Prod</temp-config>
          <rpm>0.5</rpm>
          <cycles>3</cycles>
        </system>
        <system id="2" name="suite3" type="regression">
          <temp-config>Prod</temp-config>
          <rpm>0.5</rpm>
          <cycles>3</cycles>
        </system>
        <system id="3" name="suite4" type="regression">
          <temp-config>Prod</temp-config>
          <rpm>0.5</rpm>
          <cycles>3</cycles>
        </system>
        <system id="4" name="suite5" type="regression">
          <temp-config>Prod</temp-config>
          <rpm>0.5</rpm>
          <cycles>3</cycles>
        </system>
      </test>
    </config>
    

    注意:正如其他人所指出的,标准库中有一些功能较弱的替代方案。但是,对于像这样的简单任务,它们可能非常适合,但是,如果您的 xml 文件损坏,使用标准库工具解析它们等于浪费您的时间。

    【讨论】:

      【解决方案2】:

      ElementTree 是一个不错的选择——纯 Python 并包含在标准库中,因此它是最便携的选项。但是,我总是直接访问lxml——它具有相同的 API,只是速度更快而且可以做更多事情(因为它实际上是 libxml2 的包装器)。

      from lxml import etree
      tree = etree.parse(path_to_my_xml)
      
      for elem in tree.findall('.//test'):
          assert elem.attrib['name'] == 'test02'
          elem.attrib['name'] == 'test03'
      
      for elem in tree.findall('.//temp-config'):
          assert elem.text == 'QA'
          elem.text = 'Prod'
      
      with open(path_to_output_file, 'w') as file_handle:
          file_handle.write(etree.tostring(tree, pretty_print=True, encoding='utf8'))
      

      【讨论】:

      • 对不起,我收到以下错误:Traceback(最近一次调用最后一次):文件“testrun.py”,第 13 行,在 中,open(tree, 'w') as file_handle: TypeError :强制转换为 Unicode:需要字符串或缓冲区,找到 lxml.etree._ElementTree
      • @DigitalDyn - with open(tree, 'w') as file_handle: 不是我发布的内容的一部分。我想你可能犯了复制粘贴错误:)
      • @DigitalDyn with open(file_out, 'wb') as file_handle:
      【解决方案3】:

      我建议使用 ElementTree:http://docs.python.org/2/library/xml.etree.elementtree.html

      示例:

      for atype in e.findall('type')
       print(atype.get('foobar'))
      

      或查看此主题:How do I parse XML in Python?

      【讨论】:

        【解决方案4】:

        要完成上述答案,请使用 lxml,以下是更改“名称”属性值的方法:

        from lxml import etree
        tree = etree.parse(path_to_my_xml)
        for elem in tree.xpath('.//temp-config'):
            elem.text = 'Prod'
        for elem in tree.xpath(".//test[@name='test02']"):
            elem.attrib['name'] = 'test03'
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-02-10
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多