在 Python 2.7.15 中使用 ElementTree 从 util:list 获取值
Getting values from util:list using ElementTree in Python 2.7.15
我在 python 2.7.15 上使用 etree,但我卡住了,我试图解析 XML 文件以从 it.As 获取值,您可以在下面查看我的代码:
# -*- coding: utf-8 -*-
import xml.etree.ElementTree as etree
def XMLParse(filename):
filename = filename
tree = etree.parse(filename)
beans = tree.findall('{http://www.speedframework.org/schema/beans}bean')
for bean in beans:
for property in bean:
if "name" in property.attrib and "value" in property.attrib:
print ("This one catches PROP1:" + property.attrib['name'])
print property.attrib
if "name" in property.attrib and not "value" in property.attrib:
for util in property.iter():
for lists in util:
for parameter in lists:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.attrib:
print ("This one should catch PROP2:" + parameter.attrib['value'])
print parameter.attrib
filename = open('static/test1.xml')
XMLParse(filename)
这是我的 xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.speedframework.org/schema/beans"
xmlns:cxf="http://cxf.apache.org/core"
xmlns:jaxws="http://cxf.apache.org/jaxws"
xmlns:test="http://apache.org/hello_world_soap_http"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:util="http://www.speedframework.org/schema/util"
xmlns:http="http://cxf.apache.org/transports/http/configuration"
xmlns:sec="http://cxf.apache.org/configuration/security"
xmlns:context="http://www.speedframework.org/schema/context"
xsi:schemaLocation="
http://cxf.apache.org/core
http://cxf.apache.org/schemas/core.xsd
http://www.speedframework.org/schema/beans
http://www.speedframework.org/schema/beans/speed-beans-2.0.xsd
http://www.speedframework.org/schema/context
http://www.speedframework.org/schema/context/speed-context-3.0.xsd
http://cxf.apache.org/jaxws
http://cxf.apache.org/schemas/jaxws.xsd
http://www.speedframework.org/schema/util
http://www.speedframework.org/schema/util/speed-util-2.0.xsd
http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd
http://cxf.apache.org/configuration/security
http://cxf.apache.org/schemas/configuration/security.xsd">
<context:property-placeholder location="classpath:realm.properties"/>
<bean id="FOO" class="BAR">
<property name="Prop1" value="ValueProp1" />
<property name="Prop2">
<util:list>
<value>PropValue2A</value>
<value>PropValue2B</value>
</util:list>
</property>
<property name="Prop3">
<util:map>
<entry key="Prop3Key" value-ref="Prop3Value" />
</util:map>
</property>
<property name="Prop4">
<util:list>
<ref bean="Prop4" />
</util:list>
</property>
</bean>
</beans>
如您所见,prop1、prop3 和 prop 4 正在解析 fine.The 问题出在 prop2,当我尝试获取 property.attrib 我得到的所有内容时只是 {} {} 两个空的 brackets.My 真正的 xml 大得多,这就是我使用循环的原因。但也可能有更好的解决方案我正在考虑使用 xpath 吗?
输出:
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
{}
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}
主要问题: 如何从 util:list 获取所有 "prop2"?
if 'value' in parameter.attrib:
我觉得这不对。假设 parameter
指的是 <value>PropValue2A</value>
元素。该标记是一个值元素,但它没有值属性。如果是这样,它看起来像:
<value value=whatever>PropValue2A</value>
我想你想在这种情况下检查元素的名称,而不是它的属性。
for parameter in lists:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.tag:
print ("This one should catch PROP2:" + parameter.tag)
print parameter.attrib
现在你的第三个条件将在遍历 Prop2 时通过两次:
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}
此外,我认为您的代码中的 for 循环太多了。您有五个 for 循环,但是 beans 元素的内容的最大标记深度只有四个。无论如何你都会得到合理的输出,因为 property.iter
遍历属于 属性 树的所有节点,包括它自己,所以在某些情况下循环有效地取消了。但是您可以通过仅遍历 property
的直接后代并跳过其中一个循环来简化事情。
import xml.etree.ElementTree as etree
def XMLParse(filename):
filename = filename
tree = etree.parse(filename)
beans = tree.findall('{http://www.speedframework.org/schema/beans}bean')
for bean in beans:
for property in bean:
if "name" in property.attrib and "value" in property.attrib:
print ("This one catches PROP1:" + property.attrib['name'])
print property.attrib
if "name" in property.attrib and not "value" in property.attrib:
for util in property:
for parameter in util:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.tag:
print ("This one should catch PROP2:" + parameter.tag)
print parameter.attrib
filename = open('data.xml')
XMLParse(filename)
你应该仍然得到相同的输出,而且会快一点。
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}
我在 python 2.7.15 上使用 etree,但我卡住了,我试图解析 XML 文件以从 it.As 获取值,您可以在下面查看我的代码:
# -*- coding: utf-8 -*-
import xml.etree.ElementTree as etree
def XMLParse(filename):
filename = filename
tree = etree.parse(filename)
beans = tree.findall('{http://www.speedframework.org/schema/beans}bean')
for bean in beans:
for property in bean:
if "name" in property.attrib and "value" in property.attrib:
print ("This one catches PROP1:" + property.attrib['name'])
print property.attrib
if "name" in property.attrib and not "value" in property.attrib:
for util in property.iter():
for lists in util:
for parameter in lists:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.attrib:
print ("This one should catch PROP2:" + parameter.attrib['value'])
print parameter.attrib
filename = open('static/test1.xml')
XMLParse(filename)
这是我的 xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.speedframework.org/schema/beans"
xmlns:cxf="http://cxf.apache.org/core"
xmlns:jaxws="http://cxf.apache.org/jaxws"
xmlns:test="http://apache.org/hello_world_soap_http"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:util="http://www.speedframework.org/schema/util"
xmlns:http="http://cxf.apache.org/transports/http/configuration"
xmlns:sec="http://cxf.apache.org/configuration/security"
xmlns:context="http://www.speedframework.org/schema/context"
xsi:schemaLocation="
http://cxf.apache.org/core
http://cxf.apache.org/schemas/core.xsd
http://www.speedframework.org/schema/beans
http://www.speedframework.org/schema/beans/speed-beans-2.0.xsd
http://www.speedframework.org/schema/context
http://www.speedframework.org/schema/context/speed-context-3.0.xsd
http://cxf.apache.org/jaxws
http://cxf.apache.org/schemas/jaxws.xsd
http://www.speedframework.org/schema/util
http://www.speedframework.org/schema/util/speed-util-2.0.xsd
http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd
http://cxf.apache.org/configuration/security
http://cxf.apache.org/schemas/configuration/security.xsd">
<context:property-placeholder location="classpath:realm.properties"/>
<bean id="FOO" class="BAR">
<property name="Prop1" value="ValueProp1" />
<property name="Prop2">
<util:list>
<value>PropValue2A</value>
<value>PropValue2B</value>
</util:list>
</property>
<property name="Prop3">
<util:map>
<entry key="Prop3Key" value-ref="Prop3Value" />
</util:map>
</property>
<property name="Prop4">
<util:list>
<ref bean="Prop4" />
</util:list>
</property>
</bean>
</beans>
如您所见,prop1、prop3 和 prop 4 正在解析 fine.The 问题出在 prop2,当我尝试获取 property.attrib 我得到的所有内容时只是 {} {} 两个空的 brackets.My 真正的 xml 大得多,这就是我使用循环的原因。但也可能有更好的解决方案我正在考虑使用 xpath 吗?
输出:
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
{}
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}
主要问题: 如何从 util:list 获取所有 "prop2"?
if 'value' in parameter.attrib:
我觉得这不对。假设 parameter
指的是 <value>PropValue2A</value>
元素。该标记是一个值元素,但它没有值属性。如果是这样,它看起来像:
<value value=whatever>PropValue2A</value>
我想你想在这种情况下检查元素的名称,而不是它的属性。
for parameter in lists:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.tag:
print ("This one should catch PROP2:" + parameter.tag)
print parameter.attrib
现在你的第三个条件将在遍历 Prop2 时通过两次:
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}
此外,我认为您的代码中的 for 循环太多了。您有五个 for 循环,但是 beans 元素的内容的最大标记深度只有四个。无论如何你都会得到合理的输出,因为 property.iter
遍历属于 属性 树的所有节点,包括它自己,所以在某些情况下循环有效地取消了。但是您可以通过仅遍历 property
的直接后代并跳过其中一个循环来简化事情。
import xml.etree.ElementTree as etree
def XMLParse(filename):
filename = filename
tree = etree.parse(filename)
beans = tree.findall('{http://www.speedframework.org/schema/beans}bean')
for bean in beans:
for property in bean:
if "name" in property.attrib and "value" in property.attrib:
print ("This one catches PROP1:" + property.attrib['name'])
print property.attrib
if "name" in property.attrib and not "value" in property.attrib:
for util in property:
for parameter in util:
if 'key' in parameter.attrib:
print ("This one catches PROP3:" + parameter.attrib['key'])
if 'bean' in parameter.attrib:
print ("This one catches PROP4:" + parameter.attrib['bean'])
if 'value' in parameter.tag:
print ("This one should catch PROP2:" + parameter.tag)
print parameter.attrib
filename = open('data.xml')
XMLParse(filename)
你应该仍然得到相同的输出,而且会快一点。
This one catches PROP1:Prop1
{'name': 'Prop1', 'value': 'ValueProp1'}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one should catch PROP2:{http://www.speedframework.org/schema/beans}value
{}
This one catches PROP3:Prop3Key
{'value-ref': 'Prop3Value', 'key': 'Prop3Key'}
This one catches PROP4:Prop4
{'bean': 'Prop4'}