xml文件中存储了数据,将其读到内存中有两种方式
两种方式解析xml的优缺点:
所有现代浏览器都内建了供读取和操作 XML 的 XML 解析器。
Document Object Model(缩写DOM),即文档对象模型。
解析器把 xml转换为 XML DOM 对象 - 可通过 JavaScript 操作的对象。解析器把 XML 载入内存,然后把它转换为可通过 JavaScript 访问的 XML DOM 对象。将xml文档加载进内存,形成一颗dom树(document对象),将文档的各个组成部分封装为对象。通过DOM接口,应用程序可以在任何时候访问XML文档中的任何一部分数据,这种方式称为随机访问机制
DOM 把 XML 文档作为树结构来查看。能够通过 DOM 树来访问所有元素。可以修改或删除它们的内容,并创建新的元素。元素,它们的文本,以及它们的属性,都被认为是节点。
说明,虽然js提供了解析xml的方式,但并不是很好用,下面介绍的xml解析器提供了解析xml的api,添加相关jar包到工程会使解析工作方便些
Simple APIs for XML(缩写SAX),与DOM不同,SAX提供的访问模式是一种顺序模式,这是一种快速读写XML数据的方式。,SAX解析方式逐行扫描XML文档,遇到标签时会触发解析处理器,采用事件处理的方式解析。SAX接口也被称作事件驱动接口
JAXP:sun公司提供的解析器,支持dom和sax,不过使用的不多。
JDOM,下面一个是它的升级版
DOM4J:全称是dom for java,是jdom的升级版,性能优异,使用较为广泛
dom4j是一个Java的XML API,是jdom的升级品,用来读写XML文件的。该包采用集合框架并支持DOM,SAX和JAXP等解析方式
先说dom树,将xml文档看成一棵树,用Document定义,那么根元素,用Element定义,根元素包含的元素用Element定义,Element是一个比较完整的xml元素,包含了属性,子元素,注释等,节点用Node定义,Element的子节点是Node,也可能是Element
Node在这里表示范围最大的元素,一个属性,一个文本,一个注释,一个元素都是Node
画个图说明下
其实一棵树上的每一点不管是根元素,元素,还是节点都是一个Node,Document和Element也继承了Node接口,并在它的基础上进行了扩展,为了更好的区分不同元素类型,所以区分出了Element和Node
介绍dom4j jar包中常用的几个类
XAXReader类
org.dom4j.io.SAXReader,该类的定义为xml文档的解析对象
常用方法:
Document read(File file)
Document read(URL url)
Document read(String systemId) 有多个重载的read方法用来读取xml文件,并创建Document对象
Document接口
org.dom4j.Document,继承自Branch接口,Branch接口又继承自Node接口,该接口表示XML文档
常用方法:
Element getRootElement() 获取根元素
Element接口
org.dom4j.Element,继承自Branch接口,Branch接口又继承自Node接口,该接口表示XML 元素
常用方法:
List elements()返回该元素的子元素,即xml元素
Element element(String name),根据指定名字返回子元素中的xml元素
Node node(int index)该方法继承自Branch接口,返回该元素上指定名字的子节点,子节点可能是空格,文本等,单独的文本的名字为null,值为文本
int nodeCount()该方法继承自Branch接口,返回属于这个元素的所有子节点的数量,子元素本质上也属于节点,另外空格属于一个Node,但是名字为null
String getText()该方法继承自Node接口,获取元素上的文本
String getName()该方法继承自Node接口,获取元素名称
String attributeValue(String name)获取元素的属性值,根据元素属性的名字
Iterator nodeIterator()获取子节点的迭代器
Node接口
org.dom4j.Node,在Dom树中表示最小的元素,比如一个属性,或一个注释
常用方法:
String getName()返回节点名称
String getText()返回节点中的文本
下面两个方法想要使用,需要加入相关jar包jaxen-1.1-beta-6.jar,路径为\dom4j-1.6.1\lib\jaxen-1.1-beta-6.jar
List selectNodes(String xpathExpression)根据传入的路径,获取单个节点
List selectNodes(String xpathExpression)根据传入的路径,获取指定路径下所有的Node节点
Attribute接口
org.dom4j.Attribute,表示元素的属性
常用方法:
String getValue()返回该属性的属性值
采用dom的方式读取xml文档
package xml;
import java.util.Iterator;
import java.util.List;
import org.dom4j.Attribute;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.Node;
import org.dom4j.io.SAXReader;
import org.junit.Test;
public class Dom4jTest01 {
/**
*
* 找出xml文件中第4个元素的name标签的文本
*/
@Test
public void test1() throws DocumentException {
//创建xml解析对象
SAXReader sax=new SAXReader();
//将xml文档加载到Document对象
Document doc=sax.read("src/xml01.xml");
//获取根元素
Element root=doc.getRootElement();
//获取根元素的所有子元素
List list=root.elements();
//取出根元素下第4个元素
Element fourthEle=(Element)list.get(3);
//获取该元素下名为name的子元素上的文本
String name=fourthEle.element("sex").getText();
System.out.println(name);
//获取根元素下第4个元素的子元素name下的迭代器,观察子节点是什么
Iterator it=fourthEle.element("name").nodeIterator();
int count=0;
while(it.hasNext()) {
count+=1;
System.out.println(count+"===============");
Object obj=it.next();
if (obj instanceof Node) {
Node node=(Node)obj;
System.out.println(node.getName()+"node"+node.getText());
}
if (obj instanceof Element) {
Element ele=(Element)obj;
System.out.println(ele.getName()+"element"+ele.getText());
}
}
}
// 遍历所有元素节点
@Test
public void test2() throws DocumentException {
//创建xml解析对象
SAXReader sax=new SAXReader();
//将xml文档加载到Document对象
Document doc=sax.read("src/xml01.xml");
//获取根元素
Element root=doc.getRootElement();
//遍历根元素
checkNode(root);
}
//递归遍历元素
private void checkNode(Element ele) {
//打印元素名称
System.out.println(ele.getName());
//遍历属性
for(int i=0;i
xpath方式,主要是查找xml文档中指定路径的内容
xpath方式常用的两个方法
node接口下定义了下列两个方法,Document接口间接继承了Node接口,也继承了这两个方法
List selectNodes(String xpathExpression)根据传入的路径,获取单个节点
List selectNodes(String xpathExpression)根据传入的路径,获取指定路径下所有的Node节点
注:使用xpath方式需要先导入相关jar包,\dom4j-1.6.1\lib\jaxen-1.1-beta-6.jar
xpath语法:
nodename 选取此节点。
/ 从根节点选取。
// 从匹配选择的当前节点选择文档中的节点,而不考虑它们的位置。
.. 选取当前节点的父节点。
@ 选取属性。
[@属性名] 属性过滤
[标签名] 子元素过滤
xpath解析方式示例:
package xml;
import java.util.List;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Node;
import org.dom4j.io.SAXReader;
import org.junit.Test;
public class XpathTest01 {
@Test
public void test1() throws DocumentException {
SAXReader sax=new SAXReader();
Document doc=sax.read("src/xml01.xml");
//选择第1个元素的name子元素
Node node1=doc.selectSingleNode("/students/student/name");
System.out.println(node1.getText());
//选择第2个元素的high子元素
Node node2=doc.selectSingleNode("/students/student[2]/high");
System.out.println(node2.getText());
//选择最后一个子元素的name子元素
Node node3=doc.selectSingleNode("/students/student[last()]/name");
System.out.println(node3.getText());
//选择第1个元素的id属性
Node node4=doc.selectSingleNode("/students/student/attribute::id");
System.out.println(node4.getText());
//选择第2个元素的id属性
Node node5=doc.selectSingleNode("/students/student[2]/attribute::id");
System.out.println(node5.getText());
}
@Test
public void test2() throws DocumentException{
SAXReader sax=new SAXReader();
Document doc=sax.read("src/xml01.xml");
//选择所有元素
List list=doc.selectNodes("//*");
for(int i=0;i
参考:小猴子视频