Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
python xml删除孙子或孙辈_Python_Xml_Removechild - Fatal编程技术网

python xml删除孙子或孙辈

python xml删除孙子或孙辈,python,xml,removechild,Python,Xml,Removechild,我一直在用谷歌搜索从xml文件中删除孙辈。然而,我没有找到完美的解决方案。 这是我的情况: <tree> <category title="Item 1">item 1 text <subitem title="subitem1">subitem1 text</subitem> <subitem title="subitem2">subitem2 text</subitem>

我一直在用谷歌搜索从xml文件中删除孙辈。然而,我没有找到完美的解决方案。 这是我的情况:

<tree>
    <category title="Item 1">item 1 text
        <subitem title="subitem1">subitem1 text</subitem>
        <subitem title="subitem2">subitem2 text</subitem>
    </category>

    <category title="Item 2">item 2 text
        <subitem title="subitem21">subitem21 text</subitem>
        <subitem title="subitem22">subitem22 text</subitem>
            <subsubitem title="subsubitem211">subsubitem211 text</subsubitem>
    </category>
</tree>
只有当我知道目标节点的深度时,我才能以这种风格写作。如果我只知道要删除的节点的标记名,我应该如何实现它? 伪代码:

import xml.etree.ElementTree as ET

for item in root.getiterator():
    if item.tag == 'subsubitem' or item.tag == 'subitem':
        # remove item
如果我执行
root.remove(item)
,它肯定会返回一个错误,因为item不是
root
的直接子项

编辑:
我不能安装任何第三方LIB,所以我必须用<代码> XML<代码> > < /P> < P>来删除<代码>子项目> />代码>或代码>子项< /代码>,不管它们的深度如何,请考虑下面的示例(注意,它使用的不是上游元素树):

将lxml.etree导入为etree
el=etree.fromstring(“”)
对于el.xpath('.//subsubsubitem |.//subitem')中的子项:
child.getparent().remove(子级)

通过编写递归函数,我终于在
xml
lib上完成了这项工作

def recursive_xml(root):
    if root.getchildren() is not None:
        for child in root.getchildren():
            if child.tag == 'subitem' or child.tag == 'subsubitem':
                root.remove(child)
            else:
                recursive_xml(child)
通过这样做,函数将迭代ET中的每个节点并删除我的目标节点

test_xml = r'''
<test>
    <test1>
        <test2>
            <test3>
            </test3>
            <subsubitem>
            </subsubitem>
        </test2>
        <subitem>
        </subitem>
        <nothing_matters>
        </nothing_matters>
    </test1>
</test>
'''
root = ET.fromstring(test_xml)
recursive_xml(root)
test_xml=r''
'''
root=ET.fromstring(测试xml)
递归xml(根)

希望这有助于像我这样有限制要求的人……

我是否正确理解了问题文本的意思,即在做出决定时,你实际上并不关心某个东西是孙子还是曾孙,而只关心它的标签?@charlesduff是的,你是对的。找到具有目标名称的节点并将其删除,无论其深度如何。谢谢Charles,这适用于大多数情况。但是,它需要安装
lxml
。我在大量的机器上工作,所以我必须坚持使用xml库……您是否尝试过
el.iter('subitem')
el.iter('subsubsubitem')
?我没有使用上游ElementTree的习惯,但我希望它们能够工作。
def recursive_xml(root):
    if root.getchildren() is not None:
        for child in root.getchildren():
            if child.tag == 'subitem' or child.tag == 'subsubitem':
                root.remove(child)
            else:
                recursive_xml(child)
test_xml = r'''
<test>
    <test1>
        <test2>
            <test3>
            </test3>
            <subsubitem>
            </subsubitem>
        </test2>
        <subitem>
        </subitem>
        <nothing_matters>
        </nothing_matters>
    </test1>
</test>
'''
root = ET.fromstring(test_xml)
recursive_xml(root)