第1章 XML技术
<dog>
<name>张三</name>
<age>5</age>
</dog>
1.1 什么是XML,作用是什么
-
XML 指可扩展标记语言(EXtensible Markup Language)
-
XML是用来传输数据的,不是用来显示数据的。之后学习另外一个HTML是用来显示数据的。
-
XML 标签没有被预定义。您需要自行定义标签。
-
XML 被设计为具有自我描述性(就是易于阅读)。
-
XML 是 W3C 的推荐标准
W3C在1988年2月发布1.0版本,我们现在用的就是1.0版本。在后面也有新的版本,但是新版本不太兼容旧版本,所以新版本没有被推广开。
标记,就是标签。例如:
<a></a>在html中表示超链接标签
XML在企业开发中主要有应用场景:
XML可以作为配置文件的载体,例如后续我们学习的servlet、springmvc、mybaties的配置都是通过XML进行配置的(企业开发中经常使用的)
什么是配置文件?类似于properties、ini、.txt文件,存储应用程序需要的数据的。只不过格式不一样。
开发中常见的配置文件:C3p0-config.xml web.xml (Web工程项目的核心配置文件) beans.xml(Spring框架) hibernate-config.xml(Hibernate框架) mapping.xml(Hibernate和Mybatis框架)
今天的课程中,我们主要完成如下三个问题:
1)如何去写一个XML?(重点)
2)如何去约束一个XML?(了解) 就是配置文件的规范。
3)如何去解析一个XML?(重点)把XML中的数据取出来。
1.2 如何去写一个XML(重点)
XML的编写相对来说比较简单,可以根据实际的业务场景自行编写有意义的标签和属性。例如可以在电脑中任意位置创建一个以.xml为后缀名的文件,编写描述一个人的信息的xml。也可以在idea中创建xml。
在idea中创建xml的步骤如下所示:
1)选中工程,右键new,选择File。
2)然后在弹出的框中输入创建xml的名字和后缀名,例如demo.xml,点击OK。
注意:xml文件的后缀名必须是.xml。
3)创建完成之后,在demo.xml文件中输入如下内容:
新建完xml文档之后,我们就开始在demo.xml文档中写入内容。
在向xml文档中书写内容之前,我们先来了解下xml有哪些内容组成:
xml由如下几个部分组成:
-
xml的声明 例如:
<?xml version="1.0" encoding="UTF-8"?>
A:以 <? 开始,以?>结束
B:然后后面紧跟着xml,表示当前文件是一个xml文件
C:version=”1.0”表示xml文档的版本,最开始就是1.0 ,升级以后是2.0 3.0 ,开发中使用最多的还是1.0,因为比较稳定。
D:encoding=”utf-8”表示编码 当前文件编码是UTF-8
2.标签
都是使用<>括起来的,标签名都是自定义的。 例如:
<person>
xml中的标签:
分为2大类:
双标签:<标签名 属性名=属性值 属性名=属性值></标签名>
说明:<标签名> 表示标签的开始,</标签名>表示标签的闭合,结束。
单标签:<标签名/>
注意:双标签可以在两个标签之间书写文本内容,单标签是不能书写文本内容的。
在单标签中加属性 <标签名 属性名=属性值 属性名=属性值/>
3.属性 标签的属性可以有多个,多个属性写在标签上使用空格隔开就行。
属性名也是自定义。
例如:
value="女"
4.文本 就是在标签中书写的数据。例如:柳岩
5.注释 例如:
6.字符实体
格式: &实体的名称; < 表示 < > 表示 >
说明:
xml中有5个预定义字符实体 。 字符实体相当于java中的转义字符。
xml文件中书写的标签都用<>括起来。而在xml中书写图书的时候也需要<>括起来。
所以<>能在xml中直接将图书括起来,并且能显示在浏览器上吗?
显然不能,所以针对这样一个情况我们需要特殊字符去显示。通过查阅w3cschool.CHM文档了解特殊字符如下所示:
7.CDATA区 CDATA区可以保证数据的原文输出。让文本去原样显示的。
格式:
<![CDATA[原文显示的内容]]>
部分代码实现如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<person>
<name>柳岩</name>
<age>18</age>
<sex value="女"/>
<!--
书籍想使用<>括起来 类似这样:<java开发大全>
但是我们发现这里不能直接使用<>直接括起来,会报错,那么我们想达到<>括起来的效果
应该使用xml中的字符实体:
< <
> >
如果多本书,那么都是用字符实体显得比较麻烦,所以我们可以使用CDATA区来实现
<![CDATA[书写文本内容]]> 保证文本原样显示
-->
<book><java开发大全><![CDATA[<java基础><javaweb经典讲解>]]></book>
</person>
我们学习完xml有哪些内容组成以后,我们开始学习xml的书写规范:
xml编写时也要符合一定的规则:
1)xml文件的后缀名是.xml;
2)xml文件有且只有一个根标签,不能有多个根标签;
举例:比如上述案例再加一个人,那么这里就有两个了,所以我们在上面还得在加一个根标签。
3)xml的标签是尖括号包裹关键字成对出现的,有开始标签有结束标签,关键字是自定义的;
举例:柳岩
4)xml允许有属性,属性是写在标签上面的。属性也是根据需要自定义的,属性格式:属性=“属性值”,多个属性之间使用空格隔开
5)xml是严格区分大小写的;
6)xml中的标签可以嵌套的。必须成对嵌套,不能相互嵌套;
举例:错误的标签嵌套演示:
最终代码:
<?xml version="1.0" encoding="UTF-8"?>
<persons>
<person>
<name>柳岩</name>
<age>18</age>
<sex value="女"/>
<!--
书籍想使用<>括起来 类似这样:<java开发大全>
但是我们发现这里不能直接使用<>直接括起来,会报错,那么我们想达到<>括起来的效果
应该使用xml中的字符实体:
< <
> >
如果多本书,那么都是用字符实体显得比较麻烦,所以我们可以使用CDATA区来实现
<![CDATA[书写文本内容]]> 保证文本原样显示
-->
<book><java开发大全><![CDATA[<java基础><javaweb经典讲解>]]></book>
</person>
<person>
<name>刘亦菲</name>
<age>19</age>
</person>
</persons>
1.3 如何去约束一个XML(扩展,了解)
要知道xml既然作为配置文件存储数据,那么现在我要存储2个人的信息。
创建一个xml文件,取名为persons。里面添加如下内容:
<persons>
<person>
<sex>female</sex>
</person>
<person>
<age>20</age>
</person>
</persons>
很明显:这样存储的信息是不完整的。如果存储人的信息时,那么姓名和年龄、性别等信息总得是必要的。否则我们根本就不知道存储的数据信息属于哪个人的,显得比较乱。
所以针对这样存储信息不完整的情况,我们制定了一套规则来规范我们所写的xml文件,这样的规则叫做xml的约束。
换句话说,由于xml语法中规定标签可以由开发者自己定义。导致解析时无法使用统一的代码来解析。所以引入xml的约束。
XML的约束有两种:
1)DTD约束
2)Schema约束
1.3.1 DTD约束(能够看懂即可)
1.3.1.1 什么是DTD
DTD(Document Type Definition),文档类型定义,用来约束XML文档。规定XML文档中元素的名称,子元素的名称及顺序,元素的属性等。
1.3.1.2 DTD约束的实现和语法规则(看懂dtd约束,书写符合规范的xml文件)
开发中,我们不会自己编写DTD约束文档,通常情况我们都是通过框架提供的DTD约束文档,编写对应的XML文档。
需求:接下来我们创建一个dtd约束文档,然后按照约束文档书写符合规范的xml文件。
我们先新建一个books.xml文件。
第一步:在项目下面创建一个dtd的文件夹,然后选中文件夹,鼠标右击,新创键一个books.xml文件
第二步:我们先书写books.xml文件中的内容:
<?xml version="1.0" encoding="UTF-8"?>
<books>
<book>
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book>
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
经过上述四步我们就将books.xml文件书写完毕,接下来我们开始书写DTD约束。
关于DTD约束我们能够看懂即可。如下所示就是上述books.xml文件引入了DTD约束。
简单的DTD约束就写好了,如下所示:
我们直接将如下约束复制到我们上述书写好的books.xml文件中即可,能够读懂即可。
<?xml version="1.0" encoding="UTF-8"?>
<!--
1.在xml内部定义dtd约束的声明 : <!DOCTYPE 根元素 [元素声明]>
2.xml的元素(标签)的声明: <!ELEMENT 元素名称 (元素内容)>
<!ELEMENT books (book)> 表示books标签下是book标签
<!ELEMENT book (name,author,price)> 表示的是book标签下出现的name,author,price子标签
<!ELEMENT name (#PCDATA)> 表示name标签中出现的内容是文本
-->
<!DOCTYPE books [
<!--约束根标签 book* 表示books标签下可以有多个book子标签
* + ? 和正则表达式中表示的意思是一样的
-->
<!ELEMENT books (book*)>
<!--约束book标签-->
<!ELEMENT book (name,author,price)>
<!--约束name,author,price标签
但是这三个标签下就是文本了
#PCDATA 表示标签下内容是文本
-->
<!ELEMENT name (#PCDATA)>
<!ELEMENT author (#PCDATA)>
<!ELEMENT price (#PCDATA)>
]>
<books>
<book>
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book>
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
说明:
1)xml中出现的标签,也叫做元素。那么我们书写的约束可以规范xml中到底能出现哪些标签。除此之外都不能出现。
所以xml中出现的标签都需要我们开发者在dtd约束中声明一下。只有声明了这个标签,xml中才能出现这个标签。如果约束中没有声明,那么xml中就不能出现。
所以,xml中出现的标签需要使用如下的语法(也就是xml中元素的声明语法)。
在xml内部定义dtd约束的声明 :
<!DOCTYPE 根元素 [元素声明]>
xml的元素(标签)的声明:
<!ELEMENT 元素名称 (元素内容)>
元素名:自定义。
元素内容包括:符号、数据类型和标签。
常见符号:? * + () |
常见数据类型:#PCDATA 表示内容是文本,不能是子标签。
标签:就是正常子标签。
2)由于 <!ELEMENT book (name,author,price)> 顺序是name,author,price,所以下面的顺序也得是:
<book>
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
前后顺序不能换。
接下来对上述代码的标签添加属性,比如给book属性添加一个address地址,表示将书存放到哪里。
添加属性之后的代码如下所示:
<!DOCTYPE books [
<!--约束根标签 book* 表示books标签下可以有多个book子标签
* + ? 和正则表达式中表示的意思是一样的
-->
<!ELEMENT books (book*)>
<!--约束book标签-->
<!ELEMENT book (name,author,price)>
<!--约束name,author,price标签
但是这三个标签下就是文本了
#PCDATA 表示标签下内容是文本
-->
<!ELEMENT name (#PCDATA)>
<!ELEMENT author (#PCDATA)>
<!ELEMENT price (#PCDATA)>
<!ATTLIST book address CDATA "图书馆"
id ID #REQUIRED
>
]>
<books>
<book address="藏经阁" id="a1">
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book id="a2">
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
对上述声明属性进行解释说明:
元素名称: 表示该属性使用在哪个标签上;
属性名称: 表示在标签上添加的属性名字;
属性类型: 添加的属性类型。
属性类型有如下几种:
类型 描述
**CDATA 值为字符数据 (character data) **
(en1|en2|…) 此值是枚举列表中的一个值
**ID 值为唯一的 id **
默认值: 表示最开始给属性的默认值。
值 解释
值 属性的默认值
**#REQUIRED 属性值是必需的 **
#IMPLIED 属性不是必需的
#FIXED value 属性值是固定的
1.3.2 Schema约束(能够看懂即可)
与dtd约束一样,schema它也是用来约束xml文件的。schema约束书写的时候,它遵守xml的语法规则。在书写schema的时候,就和书写xml文件的文档结构一样。
注意:书写schema文件的时候,它的文件扩展名是xsd。
1.3.2.1 书写schema约束
1、首先创建一个xml文件。然后根据xml文件书写符合规范的schema约束。
创建books.xml文件:
代码如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<books>
<book>
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book>
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
2、接下来我们需要创建一个schema文件:
步骤:
第一步:首先进入文件创建窗口,选中工程鼠标右击,new–>File,然后进入如下页面:
第二步:输入创建的文件的名称和schema文件的后缀名xsd;
第三步:因为schema约束文件本身就是xml,所以声明xml文件的头适用于schema约束的文件。
第四步:将如下的内容复制到上述已经创建好的books.xsd中。然后我们就可以书写schema约束了。
<schema xmlns="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://www.example.org/books"
elementFormDefault="qualified">
</schema>
说明:
1)schema约束的结构和xml文件书写规范是一样的,<?xml version="1.0" encoding="UTF-8"?>表示对xml的声明,是根标签;
2)xmlns=“http://www.w3.org/2001/XMLSchema” 表示此schema文件受到w3组织的指定的约束;
3)targetNamespace=“http://www.example.org/books”,叫做名称空间,这个相当于java中包的作用,区分不同约束中的不同标签。当需要被当前这个schema文件约束的xml文件,需要通过当前这个名字引入当前schema文件。
4)elementFormDefault=“qualified”,如果值为qualified,那么当前schema中所有的标签默认都是放在名称空间中的。如果值为unqualified,那么除了schema中的根标签在名称空间即 http://www.example.org/books 包中,其他的标签都不会在这个包中。在开发中,我们都是书写默认值qualified。
上述了解完成之后,接下来我们读一下一个完整的schema约束:
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://www.example.org/books"
elementFormDefault="qualified">
<!-- 在此处书写schema约束语法 -->
<element name="books">
<complexType><!-- 声明books是复杂标签 -->
<sequence><!-- 通过sequence标签指定子标签的顺序 -->
<element name="book" maxOccurs="unbounded">
<complexType>
<sequence>
<element name="name" type="string"></element>
<element name="author" type="string"></element>
<element name="price" type="double"></element>
</sequence>
<attribute name="address"></attribute>
</complexType>
</element>
</sequence>
</complexType>
</element>
</schema>
说明:
1.xml中出现的标签需要使用这样的语法来定义。即先清楚xml中需要多少个标签,在Schema文件中就书写多少个element标签。
所以xml中第一个出现的books标签需要使用来声明。
element标签中的 name属性 就是xml中 可以书写的标签的名字。
2.为了方便schema约束的书写,我们将xml中的标签简单的分为2大类:
a) 简单标签 : 标签中只有文本数据;
b) 复杂标签:标签中有子标签或者属性加上文本数据;
在element标签中需要使用complexType声明当前的element标签name属性指定的是一个复杂标签。
如果是简单标签可以使用simpleType。
3.上述在books.xml文件中我们发现books标签是复杂标签,针对复杂标签,需要在当前的标签中书写子标签来限制当前复杂标签中的其他内容。
所以我们需要使用标签来声明books标签是一个复杂标签。并且针对复杂标签中出现的子标签,我们需要使用标签来声明子标签出现的顺序。
A)books标签中出现的子标签是book,由于book也是一个标签,所以我们也需要使用标签来声明xml中的book;
B)并且book标签也是一个复杂标签,所以我们需要使用标签来声明;
C)book标签中也有子标签,所以还需要使用来声明子标签的顺序;
D)最后发现book标签在books.xml出现了多次,所以需要给加上maxOccurs="unbounded"属性。表示book标签可以出现很多次。(没有次数的限制)
大于等于1次
5.最后在里面写上book标签中出现的3个name,author,price子标签的声明。并且针对book标签中出现的属性。我们需要使用
这样的语法来声明。注意标签的位置。
在books.xml文件中增加一个address属性:
所以在books.xsd即schema约束中添加一个属性。注意标签的位置。
1.3.2.2 在xml文件中引入schema约束
在books.xml文件中引入schema约束的步骤:
第一步:首先鼠标放在根标签books后面,打个空格,然后将如下内容复制到books后面
代码如下:
<books xmlns="default namespace"
xsi:schemaLocation="{namespace} {location}"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
然后引入schema约束的图解
最终完整代码:
<?xml version="1.0" encoding="UTF-8"?>
<books xmlns="http://www.example.org/books"
xsi:schemaLocation="http://www.example.org/books books.xsd"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
>
<book address="藏经阁">
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book>
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
说明:
1)xmlns:xsi=“http://www.w3.org/2001/XMLSchema-instance”,表示当前xml文件是一个受schema约束的实例,这里不需要改变;
2)xmlns=“http://www.example.org/books”,schema约束文件中的targetNamespace的值,表示在books.xml文件中引入名称空间;
3)xsi:schemaLocation=“http://www.example.org/books books.xsd”,
schema约束文件中的targetNamespace的值 schema约束文件的路径
第2章 如何去解析一个XML(掌握)
2.1解析概述
问题:既然xml经常用作java程序的配置文件。那么java程序运行所需要的参数(数据)就需要我们通过java代码从xml配置文件中获取出来。这样的一个过程叫做xml的解析。
XML的解析就是将有用的信息从XML文档中解析出来,例如上述的books.xml,怎样通过java代码将books.xml中的属性值和文本解析出来是我们接下来要学习的内容。
2.2 常用的解析方式
DOM: 把整个XML文件作为树的方式直接加载到内存中。
优点:整个文件在内存中,可以对文件的内容进行增删改查
缺点:对内存的要求太大,可能导致内存溢出
SAX: 边读取边操作,把整个树分开,读到哪里就操作到哪里,操作完就释放内存,再去读下一段内容
优点:不占用太大的内存,不会出现内存问题
缺点:只能查询对应的内容,不能对元素做增删改操作。
2.3 常见的解析开发包
是对上面的解析方式的具体API实现,常见的解析开发包如下:
JAXP:SUN公司的官方解析技术,支持DOM解析和SAX解析。
JSOUP:功能强大DOM方式的XML解析开发包,尤其对HTML解析更加方便(项目中讲解)。网络爬虫
JDOM:开源组织的DOM方式的解析技术。与Dom4j类似。
DOM4J:JDOM的分离版 增强版,开源,完全支持 DOM,SAX解析方式,Hibernate底层的XML解析技术。
我们今天讲解的是DOM4J解析xml.
2.4 DOM4J解析技术
2.4.1 使用DOM4J的准备工作
因为dom4j技术是第三方的解析技术,所以我们需要导入第三方包。在导入包之前我们需要先了解下dom4j的结构。
导包的步骤:
第一步:首先在工程的模块中创建一个lib文件夹。
第二步:在dom4j的解压包中找到dom4j的核心包,复制到刚刚创建的lib文件夹中。
第三步:然后鼠标选中jar包,右击,选择Add as Libarary…
第四步:然后在弹出框中选择OK。
第五步:如果出现如下图所示界面,那么这样我们的导包就成功了。
2.4.2 DOM4J的API介绍
说明:如果我们想要解析xml文件中的数据,首先我们要将books.xml文件加载到计算机内存中,而xml文件被加载到内存中之后,就可以将xml看成一个树结构,我们把这个整体树结构叫做document对象。也就是说xml文件到内存中之后就是一个document对象。然后我们就可以根据document对象中的一些API 分别来获取根标签、子标签以及标签中的属性和文本内容。
关于具体如何使用DOM4J的API,我们可以查看DOM4J提供的官方文档:
使用浏览器打开index.html.
进入index.html页面之后,选择Quick start
dom4j 必须使用核心类SaxReader加载xml文档获得document,通过document对象获得文档的根元素,然后就可以操作了。
/**
* 获取name,author,price标签中的文本。
* document.getRootElement();获取根标签对象。返回值类型为Element。
* element.elements();获取标签下所有的直接子标签对象
* element.element(tagName);获取标签下指定的子标签。
*/
常用API如下:
-
SaxReader对象
a) 使用SaxReader类中的read(url) 方法加载执行xml文档来获取Document类的对象。
-
Document对象
a) 使用Document类中的**getRootElement()**方法获得根标签。返回值类型为Element。
举例:Element books = document.getRootElement();
-
Element对象
a) 使用Element类中的**elements()**方法 获得指定名称的所有子元素。
举例:List bookList = books.elements();
b) 使用Element类中的**element(tagName) **获得指定名称的子标签。
举例:Element name =book.element(“name”);
c) attributeValue(…) 获得指定属性名的属性值。
d) getText() 获得当前元素的文本内容。
name.getText();
e)String elementText(子元素名) 得到子元素中文本
2.4.3 使用DOM4J正式解析xml文件
需求:新建books.xml文件,并获取所有标签中的文本值。
1)在模块下新建一个books.xml文件,并输入内容。
<?xml version="1.0" encoding="UTF-8"?>
<books>
<book>
<name>面试宝典</name>
<author>锁哥</author>
<price>78.8</price>
</book>
<book>
<name>java从入门到精通</name>
<author>黑旋风</author>
<price>88.8</price>
</book>
</books>
2)新建包com.itheima.sh.parsexml,并在该包下新建ParseXmlTest类.
首先需要先将xml文件加载到内存中,形成Document对象。Document对象就是xml在内存中 的体现。
而我们获取xml文件中的内容就可以直接通过document对象去寻找了。
加载的代码:
@Test
public void getXmlText() throws Exception
{
//1.将xml文件加载到内存中,形成document对象
SAXReader reader = new SAXReader();
//通过reader.read("books.xml")获取document对象
Document document = reader.read("books.xml");
}
3)xml中标签的获取像剥洋葱一样,是一层一层的去获取的。
所以大体思路:
A)首先通过document对象获取books根标签对象
//2.获取根标签对象
Element books = document.getRootElement();
B)然后通过books根标签对象获取下面的所有子标签。
//3.获取books根标签下面的所有的子标签
List<Element> bookList = books.elements();
C)然后遍历集合中的所有book标签对象,获取每个book下面的name,author,price标签对象。然后打印文本值
//4.然后遍历集合中的所有book标签对象,获取每个book下面的name,author,price标签对象。
for (Element book : bookList) {
Element name = book.element("name");
Element author = book.element("author");
Element price = book.element("price");
//打印文本值
System.out.println(name.getText()+"=="+author.getText()+"=="+price.getText());
}
完整代码:
/*
* 需求:新建books.xml文件,并获取所有标签中的文本值。
*/
public class ParseXmlTest {
@Test
public void getXmlText() throws Exception
{
//1.将xml文件加载到内存中,形成document对象
SAXReader reader = new SAXReader();
//通过reader.read("books.xml")获取document对象
Document document = reader.read("books.xml");
// System.out.println(document);
//2.获取根标签对象
Element books = document.getRootElement();
//3.获取books根标签下面的所有的子标签
List<Element> bookList = books.elements();
//4.然后遍历集合中的所有book标签对象,获取每个book下面的name,author,price标签对象。
for (Element book : bookList) {
Element name = book.element("name");
Element author = book.element("author");
Element price = book.element("price");
//打印文本值
System.out.println(name.getText()+"=="+author.getText()+"=="+price.getText());
}
}
}
2.5 使用xpath技术结合DOM4J技术读取xml文件(了解)
1.概念介绍
问题:通过上面的案例我们发现有个小问题.就是获取标签的过程太过繁琐。我们需要一层一层的去获取。假设xml嵌套了50层的话,对于我们开发者来说是非常繁琐的。所以我们希望应该有这样的技术,一下子直接就能获取我们所需要的标签对象。这就是我们接下来需要学习的xpath技术。
xpath技术 也是 W3C 组织制定的快速获取 xml文件中某个标签的技术。
xpath其实就像在文件系统中定位文件,所以我们学习xpath主要学习xpath的路径表达式。
2.XPath使用步骤
步骤1:导入jar包(dom4j-1.6.1.jar(dom4j核心包)和jaxen-1.1-beta-6.jar(xpath依赖的包))
步骤2:通过dom4j的SaxReader获取Document对象
步骤3:使用document常用的api结合xpath的语法完成选取XML文档元素节点进行解析操作。
说明:
- Node叫做是节点,DOM里面所有的类型都是Node的子类
- 比如Document Element Attribute 都是 Node的子类
- Node中的两个方法可以使用XPath:
方法 | 作用 |
---|---|
List selectNodes(“表达式”) | 获取符合表达式的元素集合 |
Element selectSingleNode(“表达式”) | 获取符合表达式的唯一元素 |
3.XPath语法(了解)
在学习如何使用XPath之前,我们先将课后资料中的tianqi.xml放到项目根目录下,然后我们在演示如何使用xpath。
3.1绝对路径表达式方式
- 以/开头的路径叫做是绝对路径,绝对路径要从根元素开始写
- 需求:获取北京节点
//以/开头的路径叫做是绝对路径,绝对路径要从根元素开始写
@Test
public void demo01() throws Exception{
SAXReader reader = new SAXReader();
Document document = reader.read("tianqi.xml");
//selectNodes() 获取多个元素
List<Node> list = document.selectNodes("/天气预报/北京");
System.out.println(list.size());
//遍历集合
for (Node node : list) {
System.out.println(node); //北京
}
//selectSingleNode() 获取第一个匹配的元素
Node node = document.selectSingleNode("/天气预报/北京");
System.out.println(node); //北京
}
3.2相对路径表达式方式
- 不以/开头, 相对于当前对象的路径.就是相对当前节点元素位置继续查找节点
- 需求:用绝对路径的方式获取北京的“温度”,然后使用获取的节点的相对路径获取湿度
//不以/开头, 相对于当前对象的路径.就是相对当前节点元素位置继续查找节点
@Test
public void demo02() throws Exception{
SAXReader reader = new SAXReader();
Document document = reader.read("tianqi.xml");
//用绝对路径的方式获取“温度”
Node node = document.selectSingleNode("/天气预报/北京/温度");
//使用node的相对路径获取湿度
// ..代表返回上层位置
Node node1 = node.selectSingleNode("../湿度");
System.out.println("node1 = " + node1);//湿度
/*List<Node> list = node.selectNodes("../湿度");
for (Node node1 : list) {
System.out.println("node1 = " + node1);
}*/
}
3.3全文搜索路径表达式方式
- 代表无论中间有多少层,直接获取所有子元素中满足条件的元素
- 一个“/”符号,代表逐级写路径
- 2个“//”符号,不用逐级写路径,可以直接选取到对应的节点,是全文搜索匹配的不需要按照逐层级
- 需求1:获取天气预报里的所有湿度,不论有多少层
- 需求2:获取广州里面的3个最高温度
//代表无论中间有多少层,直接获取所有子元素中满足条件的元素
@Test
public void demo03() throws Exception {
//全文搜索 //
SAXReader reader = new SAXReader();
Document document = reader.read("tianqi.xml");
//获取天气预报里的所有湿度,不论有多少层
List<Node> list = document.selectNodes("//湿度");
//遍历打印
for (Node node : list) {
System.out.println(node.getText());
}
System.out.println("--------------");
//获取广州里面的3个最高温度
List<Node> list1 = document.selectNodes("/天气预报/广州//最高温度");
for (Node node : list1) {
System.out.println(node.getText());
}
}
3.4谓语条件查询 (了解)
-
谓语,又称为条件筛选方式,就是根据条件过滤判断进行选取节点
-
需求:获取level为A的最高温度
//谓语,又称为条件筛选方式,就是根据条件过滤判断进行选取节点 @Test public void demo04() throws Exception { SAXReader reader = new SAXReader(); Document document = reader.read("tianqi.xml"); //获取level为A的最高温度 // \叫转义符号 \" 表示这个双引号不会被java识别为字符串 //List<Node> list = document.selectNodes("//最高温度[@level=\"A\"]"); //获取最高温度中属性名是level 属性值是A的元素 List<Node> list = document.selectNodes("//最高温度[@level='A']"); //遍历集合 for (Node node : list) { //18 System.out.println(node.getText()); } }
说明://最高温度[@level=‘A’] 选择 最高温度 标签,但是要求 最高温度 必须有指定属性名level是A
第3章 XML的实际应用场景(了解)
实际开发中,我们一般会使用各种各样的框架的进行企业开发,而这些框架一般都会将某些公共的功能写好了,我们需要做的只需要按照框架提供的约束进行框架的配置就可以了,当我们使用XML配置好框架后,在运行时,框架底层会解析我们配置XML文档获取有用的信息,从而根据我们的需求实现某些功能。
所以,实际开发中我们很少会自己编写XML约束和解析XML 。主要写XML配置文件。