如何在python中使用ElementTree访问包含名称空间的xml中的属性值 [英] How to access attribute value in xml containing namespace using ElementTree in python

查看:106
本文介绍了如何在python中使用ElementTree访问包含名称空间的xml中的属性值的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

XML文件:

<?xml version="1.0" encoding="iso-8859-1"?>
<rdf:RDF xmlns:cim="http://iec.ch/TC57/2008/CIM-schema-cim13#" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#">
<cim:Terminal rdf:ID="A_T1">
<cim:Terminal.ConductingEquipment rdf:resource="#A_EF2"/>
<cim:Terminal.ConnectivityNode rdf:resource="#A_CN1"/>
</cim:Terminal>
</rdf:RDF>

我想获取Terminal.ConnnectivityNode元素的属性值和Terminal元素的属性值也作为上面的xml。我已经尝试过以下方式!

I want to get the Terminal.ConnnectivityNode element's attribute value and Terminal element's attribute value also as output from the above xml. I have tried in below way!

Python代码:

from elementtree import ElementTree as etree
tree= etree.parse(r'N:\myinternwork\files xml of bus systems\cimxmleg.xml')
cim= "{http://iec.ch/TC57/2008/CIM-schema-cim13#}" 
rdf= "{http://www.w3.org/1999/02/22-rdf-syntax-ns#}"

将以下行添加到代码中

print tree.find('{0}Terminal'.format(cim)).attrib

输出1::符合预期

{'{http://www.w3.org/1999/02/22-rdf-syntax-ns#}ID': 'A_T1'}

如果我们在下面的代码中添加以下代码

If we Append with this below line to above code

print tree.find('{0}Terminal'.format(cim)).attrib['rdf:ID'] 

output2 :rdf:ID

中的关键错误如果我们在下面的代码中追加以下内容

If we append with this below line to above code

print tree.find('{0}Terminal/{0}Terminal.ConductivityEquipment'.format(cim))

output3

如何获取 output2 作为A_T1& Output3 作为#A_CN1?

How to get output2 as A_T1 & Output3 as #A_CN1?

以上代码中{0}的含义是什么,我发现它必须通过net使用

What is the significance of {0} in the above code, I have found that it must be used through net didn't get the significance of it?

推荐答案

首先, {0} 您想知道的是Python内置字符串格式设置语法的一部分。 Python文档对语法有相当全面的指导。 ,它只会替换为 cim ,从而导致字符串 {http://iec.ch/TC57/2008/CIM-schema-cim13 #} Terminal

First off, the {0} you're wondering about is part of the syntax for Python's built-in string formatting facility. The Python documentation has a fairly comprehensive guide to the syntax. In your case, it simply gets substituted by cim, which results in the string {http://iec.ch/TC57/2008/CIM-schema-cim13#}Terminal.

这里的问题是 ElementTree 有点愚蠢命名空间。除了必须简单地提供名称空间前缀(如 cim: rdf:)之外,您还必须以XPath形式提供。这意味着 rdf:id 变为 {http://www.w3.org/1999/02/22-rdf-syntax-ns#} ID ,这很笨拙。

The problem here is that ElementTree is a bit silly about namespaces. Instead of being able to simply supply the namespace prefix (like cim: or rdf:), you have to supply it in XPath form. This means that rdf:id becomes {http://www.w3.org/1999/02/22-rdf-syntax-ns#}ID, which is very clunky.

ElementTree 确实支持使用名称空间前缀查找标签的方法 ,但不适用于属性。这意味着您必须将 rdf:扩展为 {http://www.w3.org/1999/02/22-rdf-syntax -ns#} 自己。

ElementTree does support a way to use the namespace prefix for finding tags, but not for attributes. This means you'll have to expand rdf: to {http://www.w3.org/1999/02/22-rdf-syntax-ns#} yourself.

在您的情况下,它可能如下所示(请注意, ID 区分大小写):

In your case, it could look as following (note also that ID is case-sensitive):

tree.find('{0}Terminal'.format(cim)).attrib['{0}ID'.format(rdf)]

这些替换扩展为:

tree.find('{http://iec.ch/TC57/2008/CIM-schema-cim13#}Terminal').attrib['{http://www.w3.org/1999/02/22-rdf-syntax-ns#}ID']

当这些箍跳过时,它会起作用(请注意,ID为 A_T1 而不是#A_T1 )。当然,要处理这些问题确实很烦人,因此您也可以切换到 lxml 并主要为您处理。

With those hoops jumped through, it works (note that the ID is A_T1 and not #A_T1, however). Of course, this is all really annoying to have to deal with, so you could also switch to lxml and have it mostly handled for you.

您的第三种情况不能仅仅因为1)命名为 Terminal.ConductingEquipment 而不是 Terminal.ConductivityEquipment ,以及2)如果您确实想要 A_CN1 而不是 A_EF2 ,即 ConnectivityNode 而不是 ConductingEquipment 。您可以使用 tree.find('{0} Terminal / {0} Terminal.ConnectivityNode'.format(cim))。attrib [ A_CN1 '{0} resource'.format(rdf)]

Your third case doesn't work simply because 1) it's named Terminal.ConductingEquipment and not Terminal.ConductivityEquipment, and 2) if you really want A_CN1 and not A_EF2, that's the ConnectivityNode and not the ConductingEquipment. You can get A_CN1 with tree.find('{0}Terminal/{0}Terminal.ConnectivityNode'.format(cim)).attrib['{0}resource'.format(rdf)].

这篇关于如何在python中使用ElementTree访问包含名称空间的xml中的属性值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆