[TOC]

0x00 快速入门

在前面的学习中我们知道了XML的基础用法,和它的解析器方式包括DOM和SAX方式,在Java中处理操作XML文件常用的解决方案是Jaxp、Jdom,dom4j等等,其中后者最为常用且本文学习也是采用Dom4j包进行对xml文件的处理;

XML约束文档编写
1) DTD 实例
index.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE root SYSTEM "index.dtd" >
<root>
<stu id="a_1001" gender="男">
<name>WeiyiGeek</name>
<age>20</age>
<address>中国北京东直门220号</address>
</stu>
<stu id="a_1002" gender="女">
<name>张欣欣</name>
<age>18</age>
<address>中国河北开封区小龙街道220号</address>
</stu>
</root>

index.dtd

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
<?xml version="1.0" encoding="UTF-8"?>
<!ELEMENT root (stu)*>
<!ELEMENT stu (name,age,address)>
<!ELEMENT name (#PCDATA)>
<!ELEMENT age (#PCDATA)>
<!ELEMENT address (#PCDATA)>
<!ATTLIST stu id ID #REQUIRED>
<!ATTLIST stu gender (男|女) #REQUIRED>
``

![WeiyiGeek.index](https://cdn.jsdelivr.net/gh/WeiyiGeek/blogimage/2020/1/20200215121134.png)

<br>

2)XML Schema 实例
XMLSchema.xml
```xml
<?xml version="1.0" encoding="UTF-8"?>
<root
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://www.weiyigeek.cn/XMLSchema"
xsi:schemaLocation="http://www.weiyigeek.cn/XMLSchema XMLSchema.xsd">
<stu id="1001">
<name>WeiyiGeek</name>
<age>20</age>
<address>中国北京东直门220号</address>
</stu>
<stu id="1002">
<name>张欣欣</name>
<age>18</age>
<address>中国河北开封区小龙街道220号</address>
</stu>
</root>

XMLSchema.xsd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="http://www.weiyigeek.cn/XMLSchema" xmlns:tns="http://www.weiyigeek.cn/XMLSchema" elementFormDefault="qualified">
<element name="root">
<!-- 复杂类型 -->
<complexType>
<!-- 有顺序的 -->
<sequence maxOccurs="unbounded">
<element name="stu">
<complexType>
<sequence>
<element name="name" type="string"></element>
<element name="age" type="int"></element>
<element name="address" type="string"></element>
</sequence>
<!-- 属性 -->
<attribute name="id" type="int" use="required"></attribute>
</complexType>
</element>
</sequence>
</complexType>
</element>
</schema>

实验的项目结构:

WeiyiGeek.Dom4j

WeiyiGeek.Dom4j


0x01 基本用法

Dom4j的使用流程:

  • 1.创建SAXReader对象
  • 2.指定读取解析的xml
  • 3.获取根元素document.getRootElement();
  • 4.根据元素获取子元素或者下面的子孙元素:
    • rootElement.element(“子元素标签”):获取该元素下第一个子元素标签对象
    • rootElement.elements:获取所有子元素标签对象;

基础示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
package com.weiyigeek.xml;

import java.io.File;
import java.util.List;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;

/***
*
* @author Administrator
* 功能:验证Dom4j解析XML包
*/

public class Dom4j_demo1 {
public static void main(String[] args) {
// TODO Auto-generated method stub
//1.建立reader读取对象
SAXReader reader = new SAXReader();
try {
//2.读取指定的xml源文件
Document document = reader.read(new File("src/xml/index.xml"));
System.out.println("读取XML源文件地址: " + document.getName());

//3.获取xml中根元素
Element rootElement = document.getRootElement();
System.out.println("根元素名称: " + rootElement.getName());

//4.得到子元素和子子(子孙)元素
System.out.println("子元素名称" + rootElement.element("stu").getName());
System.out.println("子子元素名称: " + rootElement.element("stu").element("name").getName());

//5.获取所有元素及其属性
List<Element> element = rootElement.elements();
for (Element ele : element) {
String name = ele.element("name").getStringValue();
String age = ele.element("age").getText();
String addr = ele.elementText("address");
System.out.println(ele.attributeValue("id")+ ":" + name + "-" + age + "-" + addr);
}
} catch (DocumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}

执行结果:

1
2
3
4
5
6
读取XML源文件地址: file:///F:/Study-Promgram/JAVAWeb/xml/src/xml/index.xml
根元素名称: root
子元素名称stu
子子元素名称: name
1001:WeiyiGeek-20-中国北京东直门220
1002:张欣欣-18-中国河北开封区小龙街道220


0x02 Xpath基础使用

描述:在dom4j里面支持xpath的写法,xpath其实是xml的路径语言,支持我们再解析xml的时候,能够快速的定位到具体的某一个元素中;

实验结构:

WeiyiGeek.

WeiyiGeek.

使用流程:

  • 1.添加jaxen-1.1-beta-6.jar依赖流程;
  • 2.在查找指定节点时候根据XPath语法规则来查询;
  • 3.利用Xpath获取节点采用rootElement.selectSingleNode(“//name”)和rootElement.selectNodes(“//name”)

基础示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
package com.weiyigeek.xml;

import java.io.File;
import java.util.List;

import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;

/***
*
* @author Administrator
* 功能:验证XPATH的使用
*/

public class Dem4j_demo2 {
public static void main(String[] args) {
try {
// TODO Auto-generated method stub
//1.创建SAX读取对象
SAXReader reader = new SAXReader();

//2.读取xml源文件
Document document = reader.read(new File("src/xml/index.xml"));

//3.根元素
Element rootElement = document.getRootElement();

//4.使用xpath选取单个节点对象
Element xpathElement = (Element) rootElement.selectSingleNode("//name");
System.out.println("获取一个子孙元素的值: " + xpathElement.getText());

//5.使用xpath获取多个相同节点属性的值
List<Element> list = rootElement.selectNodes("//name");
for(Element xpath : list){
System.out.println(xpath.getName() + ":" + xpath.getStringValue());
}

} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
}

执行结果:
1
2
3
获取一个子孙元素的值: WeiyiGeek
name:WeiyiGeek
name:张欣欣