Python自带xml模块实现xpath查询带xmlns命名空间的xml

摘要:
在检查了Internet之后,大多数人建议使用lxml模块而不是本机xml进行查询。第三方库非常强大,但lxml需要单独安装,这不够通用。我希望尽可能使用系统的原生xml。用于xpath表达式的开头,以指示相对路径。以{http://opengis.net/kml/2.2XXX很奇怪我注意到,这不仅仅是标记中的额外字段。此外,xmlns的全名是xmlnamespace,它类似于C++命名空间。它用于解决本地名称重复冲突。此外,如果存在xmlns,则需要指定一个命名空间字典,以便在XPath查询期间导航。

需求

手上有个项目需要解析xml数据,参考写爬虫的经验,容易想到使用XPath语句进行节点导航。

XPath 是一门在 XML 文档中查找信息的语言,用于在 XML 文档中通过元素和属性进行导航。
XPath 使用路径表达式来选取 XML 文档中的节点或者节点集。这些路径表达式和我们在常规的电脑文件系统中看到的表达式非常相似。

查阅

网上搜了一下,大多推荐使用lxml模块而非自带的xml进行查询,三方库确实强大,但lxml需要单独安装,通用性不足,希望尽量用系统自带的xml实现。

文档指出xml.etree.ElementTree可以通过支持的有限的XPath表达式来定位元素,支持语法如下:

语法说明
tag查找所有具有指定名称tag的子元素。例如:country表示所有名为country的元素,country/rank表示所有名为country的元素下名为rank的元素。
*查找所有元素。如:*/rank表示所有名为rank的孙子元素。
.选择当前元素。在xpath表达式开头使用,表示相对路径。
//选择当前元素下所有级别的所有子元素。xpath不能以“//”开头。
..选择父元素。如果视图达到起始元素的祖先,则返回None(或空列表)。起始元素为调用find(或findall)的元素。
[@attrib]选择具有指定属性attrib的所有子元素。
[@attrib='value']选择指定属性attrib具有指定值value的元素,该值不能包含引号。
[tag]选择所有具有名为tag的子元素的元素。
[.='text']Python3.7+,选择元素(或其子元素)完整文本内容为指定的值text的元素。
[tag='text']选择元素(或其子元素)名为tag,完整文本内容为指定的值text的元素。
[position]选择位于给定位置的所有元素,position可以是以1为起始的整数、表达式last()或相对于最后一个位置的位置(如:last()-1)

上述完全能够涵盖我的查询工作,决定实现。

实现

代码如下

import xml.etree.cElementTree as ET

tree = ET.ElementTree(file="./reference.kml")
marks = tree.findall(".//Placemark")

注意这里的XPath不支持直接用//而要写作.//
上述代码没有报错,但返回list始终为[]无法匹配节点

思考

进入debug console查看tree变量显示存在根节点,也可以用tree[0][1][2]进行导航,我???
查看tag名称显示为{http://opengis.net/kml/2.2}XXX比较奇怪

此时xml文件开头的<kml xmlns="http://opengis.net/kml/2.2">引起了我的注意
这不就是tag里多出来的字段?

进一步查阅,xmlns全称为xml namespace类似C++的命名空间,用于解决局部名称重复冲突。
进一步的,存在xmlns则需要在XPath查询时指定namespace字典进行导航。

解决

添加namespaces属性即可

import xml.etree.cElementTree as ET
NS = {"i":"http://opengis.net/kml/2.2"}
tree = ET.ElementTree(file="./reference.kml")
marks = tree.findall(".//i:Placemark",namespaces=NS)

查询正常,能够返回匹配的list结果。

免责声明:文章转载自《Python自带xml模块实现xpath查询带xmlns命名空间的xml》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇python文件运行报错:Error: Please select a valid Python interpreteroracle 层次化查询(生成菜单树等)下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

C语言两个libxml2库使用的问题

最近使用libxml2想做点东西,翻看一些example后还是有些疑问,去segmentfault问了下,感谢@pingjiang的热心解答,问题解决,记录如下 (一)如下是一个XML文件,p为根结点 <p> <one>1</one> <two>2</two> <th...

shiro框架 4种授权方式 说明

1. shiro的配置文件(applicationContext-shiro.xml)中使用filterChain过滤url的方式 详细配置看注释 <?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/bean...

WPF实现TextBox水印效果

通常情况下,在使用文本框的时候,一般会在文本框上放一段水印文字,今天用WPF来实现一下 创建一个用户控件 一般像这种常用的,最好是自己写成用户控件,防止复制粘贴大量冗余代码 XAML: <TextBox x: xmlns="http://schemas.microsoft.com/winfx/2006/xaml/prese...

xpath和css selector的使用方法

什么是Xpath? XPath是XML的路径语言,通俗一点讲就是通过元素的路径来查找到这个标签元素 Xpath的练习建议安装火狐浏览器后,下载插件,FireBug和FirePath,谷歌浏览器可以下载ChroPath插件,进行定位,切换到XPath,默认死格式 先写//*代表定位页面下所有元素,[@id='kw'],尽量不要用xpath来定位,因为xpa...

Android应用开发中的风格和主题(style,themes)

      越来越多互联网企业都在Android平台上部署其客户端,为了提升用户体验,这些客户端都做得布局合理而且美观.......Android的Style设计就是提升用户体验的关键之一。Android上的Style分为了两个方面: Theme是针对窗体级别的,改变窗体样式; Style是针对窗体元素级别的,改变指定控件或者Layout的样式。  ...

idea 配置mapper.xml代码提示

从代码跳转mapper文件的插件: 在mapper文件中添加dtd约束: 1、下载dtd约束文件 http://mybatis.org/dtd/mybatis-3-config.dtdhttp://mybatis.org/dtd/mybatis-3-mapper.dtd 2、手动导入dtd file-->settings-->Laguage&...