【问题标题】:How do I remove last sibling nodes with the same tag?如何删除具有相同标签的最后一个兄弟节点?
【发布时间】:2013-08-09 16:57:02
【问题描述】:

我无法使用 xml.etree.ElementTree 删除某些元素。我发现了类似的情况here,但这并不能解决我的问题。我还阅读了ElementTreeXPath 上的文档。

我有一个类似的 xml 树

<metadata>
    <lineage>
        <srcinfo></srcinfo>
        <procstep>
            <otherinfo></otherinfo>
        </procstep>
        <procstep>
            <otherinfo></otherinfo>
        </procstep>
        <procstep>
            <otherinfo></otherinfo>
        </procstep>
        <procstep>
            <otherinfo></otherinfo>
        </procstep>
    </lineage>
</metadata>

假设我想删除第二个、第三个和第四个 procstep 元素。我尝试了以下代码,结果出现“ValueError:list.remove(x):x not in list”错误。

while len(root.findall('.//lineage/procstep')) > 1:
        root.remove(root.findall('.//lineage/procstep[last()]'))

关于为什么这不起作用的任何建议?还有其他方法可以解决我的问题吗?提前感谢您的任何建议。

【问题讨论】:

    标签: python xml xpath elementtree


    【解决方案1】:

    删除最后一个procstep

    要删除 procstep 元素,请使用 procstep 的父级 (lineage)。

    试试:

    lineage = root.find('.//lineage')
    last_procstep = lineage.find('./procstep[last()]')
    lineage.remove(last_procstep)
    

    如果你使用lxml,你可以使用getparent(),如下:

    last_procstep = root.find('.//lineage/procstep[last()]')
    last_procstep.getparent().remove(last_procstep)
    

    删除 procstep 元素,但第一个

    lineage = root.find('.//lineage')
    for procstep in tuple(lineage.iterfind('./procstep'))[1:]:
        lineage.remove(procstep)
    

    【讨论】:

    • 感谢 falsetru,它可以删除最后一个元素。您将如何删除除第一个 procstep 元素之外的所有元素?
    • @Barbarossa,使用.//lineage/procstep[position()&gt;1]
    • 谢谢,但这并不能解决我的问题。我见过lxml的使用,但我使用的是ElementTree。有没有办法用我所拥有的做我所要求的?我相信 ElementTree 不支持 [position] 谓词
    • @Barbarossa,我回答中的第一个代码在 ElementTree 和 lxml 中都可以使用。
    • 正是我想要的。对困惑感到抱歉。再次感谢。
    猜你喜欢
    • 2014-02-05
    • 1970-01-01
    • 2016-10-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-03-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多