我正在使用lxml来解析xsd文件,并且正在寻找一种简单的方法来删除附加到每个元素名称的URL命名空间。这是xsd文件:
<?xml version="1.0" encoding="utf-8"?>
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" version="2.0" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="rootelement">
<xs:complexType>
<xs:choice maxOccurs="unbounded">
<xs:element minOccurs="1" maxOccurs="1" name="element1">
<xs:complexType>
<xs:all>
<xs:element name="subelement1" type="xs:string" />
<xs:element name="subelement2" type="xs:integer" />
<xs:element name="subelement3" type="xs:dateTime" />
</xs:all>
<xs:attribute name="id" type="xs:integer" use="required" />
</xs:complexType>
</xs:element>
</xs:choice>
<xs:attribute fixed="2.0" name="version" type="xs:decimal" use="required" />
</xs:complexType>
</xs:element>
</xs:schema>
并使用此代码:
from lxml import etree
parser = etree.XMLParser()
data = etree.parse(open("testschema.xsd"),parser)
root = data.getroot()
rootelement = root.getchildren()[0]
rootelementattribute = rootelement.getchildren()[0].getchildren()[1]
print "root element tags"
print rootelement[0].tag
print rootelementattribute.tag
elements = rootelement.getchildren()[0].getchildren()[0].getchildren()
elements_attribute = elements[0].getchildren()[0].getchildren()[1]
print "element tags"
print elements[0].tag
print elements_attribute.tag
subelements = elements[0].getchildren()[0].getchildren()[0].getchildren()
print "subelements"
print subelements
我得到以下输出
root element tags
{http://www.w3.org/2001/XMLSchema}complexType
{http://www.w3.org/2001/XMLSchema}attribute
element tags
{http://www.w3.org/2001/XMLSchema}element
{http://www.w3.org/2001/XMLSchema}attribute
subelements
[<Element {http://www.w3.org/2001/XMLSchema}element at 0x7f2998fb16e0>, <Element {http://www.w3.org/2001/XMLSchema}element at 0x7f2998fb1780>, <Element {http://www.w3.org/2001/XMLSchema}element at 0x7f2998fb17d0>]
当我拉取标签数据时,我不希望“{http://www.w3.org/2001/XMLSchema}”出现(更改xsd文件不是一个选项)。我需要xsd标记信息的原因是我使用它来验证一系列平面文件中的列名。在“元素”级别,我正在拉动多个元素,以及子元素,我使用字典来验证列。此外,任何有关改进上述代码的建议都会很大,例如使用较少的“getchildren”调用,或者只是让它更有条理。
答案 0 :(得分:3)
我会用:
print elem.tag.split('}')[-1]
但您也可以使用xpath函数local-name()
:
print elem.xpath('local-name()')
对于较少getchildren()
次来电:只是将它们排除在外。 getchildren()
是一种不推荐使用的方式来制作直接子项列表(如果您真的需要,则应该使用list(elem)
)。
您可以迭代,或直接在元素上使用索引。例如:rootelement[0]
会为您提供rootelement
的第一个子元素(但比使用rootelement.getchildren()[0]
更有效,因为这会像list(rootelement)
一样创建一个新元素列表第一)
答案 1 :(得分:1)
我想知道为什么etree.XMLParser(ns_clean=True)
不起作用。它对我没有用,所以它从括号中的root.nsmap获取命名空间并用空字符串
print rootelement[0].tag.replace('{%s}' %root.nsmap['xs'], '')
答案 2 :(得分:0)
最简单的方法是使用字符串切片来删除名称空间前缀:
>>> print rootelement[0].tag[34:]
complexType
答案 3 :(得分:0)
如果URI未来可能会发生变化(由于某些未知原因或您确实是偏执狂),请考虑以下事项:
print "root element tags"
tag, nsmap, prefix = rootelement[0].tag, rootelement[0].nsmap, rootelement[0].prefix
tag = tag[len(nsmap[prefix]) + 2:]
print tag
这是一个非常不可能的案例,但谁知道呢?