如何缩短lxml中的过滤器查询

时间:2016-06-07 01:44:49

标签: xml parsing xml-parsing namespaces lxml

我正在使用lxml解析具有自定义名称空间的xml。下面给出了xml的摘录。

<abcd:ABCDCfg xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:abcd="http://www.xyzv.com/abcd">
   <abcd:Section name="Features" display-name="Features" desc=“Parameters”>
     <abcd:Param name=“mode”>
        <abcd:Type>string</abcd:Type>
        <abcd:Persistent>true</abcd:Persistent>
        <abcd:Configurable>true</abcd:Configurable>
        <abcd:ReadAccess>aup</abcd:ReadAccess>
        <abcd:WriteAccess>ap</abcd:WriteAccess>
        <abcd:DisplayName>Mode</abcd:DisplayName>
     </abcd:Param>
   </abcd:Section>
</abcd:ABCDCfg>

现在,当我在xml中找到我正在使用的值

sections = xmltree.findall('{http://www.xyzv.com/abcd}Section')
if (child.tag =='{http://www.xyzv.com/abcd}Param')

无论如何在lxml中都可以使用lxml而不使用命名空间。像

这样的东西
sections = xmltree.findall('Section')
if (child.tag =='Param')

这将使代码真正可读。欢迎任何帮助。

1 个答案:

答案 0 :(得分:1)

如果这适用于您的情况,您可以在解析后从树中删除所有名称空间。我会去this solution。 Python 3中的工作示例:

import lxml.etree as ET
from io import BytesIO


data = b"""<abcd:ABCDCfg xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:abcd="http://www.xyzv.com/abcd">
   <abcd:Section name="Features" display-name="Features" desc="Parameters">
     <abcd:Param name="mode">
        <abcd:Type>string</abcd:Type>
        <abcd:Persistent>true</abcd:Persistent>
        <abcd:Configurable>true</abcd:Configurable>
        <abcd:ReadAccess>aup</abcd:ReadAccess>
        <abcd:WriteAccess>ap</abcd:WriteAccess>
        <abcd:DisplayName>Mode</abcd:DisplayName>
     </abcd:Param>
   </abcd:Section>
</abcd:ABCDCfg>"""

it = ET.iterparse(BytesIO(data))
for _, el in it:
    if '}' in el.tag:
        el.tag = el.tag.split('}', 1)[1]  # strip all namespaces
root = it.root

sections = root.findall('Section')
print(sections)

打印:

[<Element Section at 0x10636d0c8>]

这意味着我们可以在树中找到元素而不指定名称空间。