您的位置:首页 > 其它

利用xpath提取xml文档数据

2018-01-14 21:43 246 查看
之所以要引入xpath的概念,目的就是为了在匹配xml文档结构树时能够准确地找到某一个节点元素。可以把xpath比作文件管理路径:通过文件管理路径,可以按照一定的规则查找所需要的文件;同样,依据xpath所制定的规则,也可以很方便地找到xml结构文档树种的任何一个节点。

W3C将其独立作为XSLT的配套标准颁布,它是XSLT以及XPointer的重要组成部分。

XPath可分为四种数据类型:

1、节点集(node-set)

节点集是通过路径匹配返回的符合条件的一组节点的集合。其它类型的数据不能转换为节点集。

2、布尔值(boolean)

由函数或布尔表达式返回的条件匹配值,与一般语言中的布尔值相同,有true和false两个值。布尔值可以和数据类型、字符串类型相互转换。

3、字符串(string)

字符串即包含一系列字符的集合,XPath中提供了一系列的字符串可与数值类型、布尔值类型的数据相互转换。

4、数值(number)

在XPath中数值为浮点数,可以是双精度64位浮点数。另外包括一些数值的特殊描述,如非数值NaN(Not-a-Number)、正无穷大、负无穷大、正负0等等。number的整数可以通过函数取得。另外,数值也可以和布尔类型、字符串类型相互转换。

其中后三种数据类型与其它编程语言中相应的数据类型差不多,只是第一种数据类型是XML文档树的特有产物。

另外,由于XPath包含的是对文档结构树的一系列操作,因此搞清楚XPath节点类型是很有必要的。一个XML文件可以包括元素、CDATA、注释、处理指令等逻辑要素,其中元素还可以包含 属性,并可以利用属性来定义命名空间。相应地,在XPath中,将节点划分为七种节点类型:

1、根节点(Root Node)

根节点是一棵树的最上层,根节点是唯一的。树上其它所有元素节点都是它的子节点或后代节点。对根节点的处理机制与其它节点相同。在XSLT中对树的匹配总是先从根节点开始。

2、元素节点(Element Nodes)

元素节点对应于文档中的每一个元素,一个元素节点的子节点可以是元素节点、注释节点、处理指令节点和文本节点。可以为元素节点定义一个唯一的标识id。

元素节点都可以有扩展名,它是由两部分组成的:一部分是命名空间URI,另一部分是本地的命名。

3、文本节点(Text Nodes)

文本节点包含了一组字符数据,即CDATA中包含的字符。任何一个文本节点都不会有紧邻的兄弟文本节点,而且文本节点没有扩展名。

4、属性节点(Attribute Nodes)

每 一个元素节点有一个相关联的属性节点集合,元素是每个属性节点的父节点,但属性节点却不是其父元素的子节点。这就是说,通过查找元素的子节点可以匹配出元 素的属性节点,但反过来不成立,只是单向的。再有,元素的属性节点没有共享性,也就是说不同的元素节点不共有同一个属性节点。

对缺省属性的处理等同于定义了的属性。如果一个属性是在DTD声明的,但声明为#IMPLIED,而该属性没有在元素中定义,则该元素的属性节点集中不包含该属性。

此外,与属性相对应的属性节点都没有命名空间的声明。命名空间属性对应着另一种类型的节点。

5、命名空间节点(Namespace Nodes)

每一个元素节点都有一个相关的命名空间节点集。在XML文档中,命名空间是通过保留属性声明的,因此,在XPath中,该类节点与属性节点极为相似,它们与父元素之间的关系是单向的,并且不具有共享性。

6、处理指令节点(Processing Instruction Nodes)

处理指令节点对应于XML文档中的每一条处理指令。它也有扩展名,扩展名的本地命名指向处理对象,而命名空间部分为空。

7、注释节点(Comment Nodes)

注释节点对应于文档中的注释。

下面,我们来构造一棵XML文档树,作为后面举例的依托:

<A id="a1">
<B id="b1">
<C id="c1">
<B name="b"/>
<D id="d1"/>
<E id="e1"/>
<E id="e2"/>
</C>
</B>
<B id="b2"/>
<C id="c2">
<B/>
<D id="d2"/>
<F/>
</C>
<E/>
</A>


现在,我们来介绍一些XPath中节点配置的基本方法。

1、路径配置

路径匹配与文件路径的表示相仿,比较好理解。有以下几个符号:

符号含义举例匹配结果
/指示节点路径/A/C/D节点”A”的子节点”C”的子节点”D”,即id值为d2的D节点
//所有路径以”//”后指定的子路径结尾的元素//E所有E元素,结果是所有三个E元素
*路径的通配符/A/B/C/*A元素→B元素→C元素下的所有子元素,即name值为b的B元素、id值为d1的D元素和id值为e1和e2的两个E元素
I逻辑或//B I //C所有B元素和C元素
2、位置匹配

对于每一个元素,它的各个子元素是有序的。如:

举 例含 义匹配结果
/A/B/C[1]A元素→B元素→C元素的第一个子元素name值为b的B元素
/A/B/C[last()]A元素→B元素→C元素的最后一个子元素id值为e2的E元素
/A/B/C[position()>1]A元素→B元素→C元素之下的位置号大于1的元素id值为d1的D元素和两个具有id值的E元素
3、条件匹配

条件匹配就是利用一些函数的运算结果的布尔值来匹配符合条件的节点。常用于条件匹配的函数有四大类:节点函数、字符串函数、数值函 数、布尔函数。例如前面提到的last()、position()等等。这些功能函数可以帮助我们精确寻找需要的节点。

函数及功能作用

//函数及功能作用
count()功能
//统计计数,返回符合条件的节点的个数
number()功能
//将属性的值中的文本转换为数值
substring() 功能
//语法:substring(value, start, length)

//截取字符串

sum()功能

//求和


这些功能只是XPath语法中的一部分,还有大量的功能函数没有介绍,而且目前XPath的语法仍然在不断发展中。通过这些函数我们可以实现更加复杂的查询和操作。

以上这些匹配方法中,用得最多的还要数路径匹配。依靠给出相对于当前路径的子路径来定位节点的。

用SelectSingleNode()和SelectNodes()搜索结点
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
XmlDocument doc = new XmlDocument();//建立文档对象
try
{
doc.Load("http://www.cnblogs.com/myOrder.xml");
XmlNode root = doc.DocumentElement;//获取文档的根节点
XmlNode temp;
temp = root.SelectSingleNode("姓名");
Console.WriteLine("(查找1)" + temp);
temp = root.SelectSingleNode("定购人信息/姓名");
Console.WriteLine("(查找2)" + temp.Name+":"+temp.InnerText);
temp = root.SelectSingleNode("订货信息/商品/品名");
Console.WriteLine("(查找3)" + temp.Name + ":" + temp.InnerText);
XmlNodeList templist = root.SelectNodes("订货信息/商品/品名");
Console.WriteLine("(查找4)");
foreach (XmlNode nodeinlist in templist)
{
Console.WriteLine(nodeinlist.Name + ":" + nodeinlist.InnerText);
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
Console.ReadLine();//辅助代码,用于保留控制台窗口
}
}
}


在xml搜索节点(两种方法)
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
XmlDocument doc = new XmlDocument();//建立文档对象
try
{
doc.Load("http://www.cnblogs.com/myOrder.xml");
//在xmlDocument对象中搜索元素
Console.WriteLine("");
XmlNodeList myNodeList = doc.GetElementsByTagName("品名");
for (int i = 0; i < myNodeList;i++ )
{
Console.WriteLine(myNodeList[i].Name+":"+myNodeList[i].InnerText);
}
//在xmlElement对象中搜索元素
Console.WriteLine("在xmlElement对象中搜索元素");
XmlElement myElement = doc.DocumentElement;
myElement = (XmlElement)myElement.LastChild;
myNodeList = myElement.GetElementsByTagName("品名");
for (int i = 0; i < myNodeList; i++)
{
Console.WriteLine(myNodeList[i].Name + ":" + myNodeList[i].InnerText);

}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
Console.ReadLine();//辅助代码,用于保留控制台窗口
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: