
XML作为一种便捷的数据操作和数据传输的工具,在现今的WEB开发中发挥着越来越重要的作用,使得针对XML文档的操作也越来越频繁,一些用于处理XML文件的组件便应运而生,DOM和SAX就是常用的两种。它们虽然都已经能够实现对XML文档的操作,但是缺陷也是明显的。例如,DOM是用IDL定义的跨语言API,只限于所有编程语言都能提供的特性和类,这样既不能充分利用Java,也不符合Java的最佳做法、命名规则和编码标准。另外,DOM通过在内存中建立一个XML元素树实现对XML数据的访问,这样做导致了要维护一个树形的数据结构时大量占用系统资源,主要是内存的资源。相比较于DOM,SAX是面向标签用回调方式进行XML访问的,由于不需要建立树,资源负担较轻,但SAX仅能进行顺序检索,不支持对文件各部分的随机访问,很少被单独用来操作XML文档。为克服以上的缺陷,2000年,一种新的用于处理XML文档的组件JDOM诞生了。JDOM是一个开放源代码的API,它基于树型结构,利用纯Java技术实现了对XML文档的分析、建立、处理和序列化。
JDOM的开发结合了DOM与SAX的优点。与DOM相似,JDOM将XML文档表示为树,包括元素、属性、说明、处理指令等,树的数据可以来自数据库之类的非XML库、Java程序中的直接量或来自计算。JDOM本身不包含分析器,而是依赖于SAX分析器,将XML文档读取到JDOM中。同时,JDOM还可以将DOM Document对象转换成JDOM Document对象,从而将DOM程序的输出导向JDOM程序的输入。JDOM不但可以读入DOM或SAX的内容,也可以输出DOM和SAX可以接收的格式。
JDOM的另一个特点是它被设计成一个可以在小内存上快速执行轻量级API,它不要求把整个XML文件放入内存,而是只在需要时把信息装入内存,从而减少了系统资源开销。JDOM提供了足够的文件视图供随机访问XML数据,并且JDOM树是完全读写的,除了受通常的XML限制之外,树的所有部分都可以移动、添加或删除。
JDOM是由以下几个包组成的
(1) org.jdom,包含了所有的XML文档要素的Java类,这些类是解析XML文件时所要用
到的所有数据类型,如Attribute CDATA、Comment 、DocType 、Document 、Ele2ment、
EntityRef 、Namespace 、ProcessingInstruction 和Text 类。
(2) org.jdom.input,包含了读取XML文档的类,一般用于文档的创建工作,其中最常用的构造器类是SAXBulider。
(3) org.jdom.output,包含了写入XML文档的类,用于文档转换输出,最常用的输出类是XMLOutputter。
(4) org.jdom.adapters,包含了与DOM适配的java类,以便连接各种DOM解析器实现, 并
获取W3C DOM 文档对象, 以允许JDOM使用任何第三方厂商的解析器。
(5) org.jdom.filter,包含了XML文档的过滤器类。
(6) org.jdom.transform,包含了将JDOM XML文档接口转换为其他XML文档接口, 这些
类是基于JAXP的TrAX类. 它包含JDOM的转换类JDOMTransformer , 支持简单的单行代码
转换。
(7) org.jdom.xpath,包含了对XML文档XPATH操作的类三、JDOM类说明[3]。这个包里的类是你解析xml文件后所要用到的所有数据类型。
Attribute
CDATA
Coment
DocType
Document
Element
EntityRef
Namespace
ProscessingInstruction
Text
org.JDOM.transform
在涉及xslt格式转换时应使用下面的2个类
JDOMSource
JDOMResult
org.JDOM.input
输入类,一般用于文档的创建工作
SAXBuilder
DOMBuilder
ResultSetBuilder
org.JDOM.output
输出类,用于文档转换输出
XMLOutputter
SAXOutputter
DomOutputter
JtreeOutputter
使用前注意事项:
1.JDOM对于JAXP以及TRax的支持
JDOM 支持JAXP1.1:你可以在程序中使用任何的parser工具类,默认情况下是JAXP的parser。
制定特别的parser可用如下形式
SAXBuilder parser
Document doc = parser.build("http://www.cafeconleche.org/");
JDOM也支持TRaX:XSLT可通过JDOMSource以及JDOMResult类来转换(参见以后章节)
2.注意在JDOM里文档(Document)类由org.JDOM.Document来表示。这要与org.w3c.dom中的Document区别开,这2种格式如何转换在后面会说明。
以下如无特指均指JDOM里的Document。
JDOM的主要使用方法:
(1)使用JDOM首先要指定使用什么解析器。如:
(2)得到Document,我们以后要进行的所有操作都是对这个Document操作的:
(3)得到根元素:
在JDOM中所有的节点(DOM中的概念)都是一个org.jdom.Element类,当然他的子节点也是一个org.jdom.Element类。
(4)得到元素(节点)的集合:
这表示得到“books”元素的所在名称为“book”的元素,并把这些元素都放到一个List集合中
(5)轮循List集合
还有一种轮循方法是:
(6)取得元素的属性:
(7)取得元素的子元素(为最低层元素)的值:
(8)改变元素(为最低层元素)的值:
(9)保存Document的修改到XML文件中:
outputter.output(doc,new FileOutputStream(xmlpath));
JDOM 可以被用来解析现有的XML 文档,并且十分方便。大致过程如下:
(1) 用简单无变元构造函数构造一个org.jdom.input.SAXBuilder 对象:
SAXBuilder sb = new SAXBuilder();
(2) 用建立器的build()方法从Reader,InputStream,URL,File 或包含系统ID 的字
符串建立Document 对象:
Document myDocument = sb.build(/some/directory/myFile.xml);
(3) 如果读取文档遇到问题,则抛出IOException;如果建立文档遇到问题,则抛出
JDOMException。
(4) 如没有出现问题,则用Document 类、Element 类和其他JDOM 类的方法在文档
中导航。
具体代码实例如下:
package XML;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Iterator;
import java.util.List; //下面是引用到JDOM中的类
import org.jdom2.Document;
import org.jdom2.Element;
import org.jdom2.JDOMException;
import org.jdom2.input.SAXBuilder;
import org.jdom2.output.XMLOutputter;
public class JDomParse {
}
package test;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Iterator;
import java.util.List; //下面是引用到JDOM中的类
import org.jdom2.Document;
import org.jdom2.Element;
import org.jdom2.JDOMException;
import org.jdom2.input.SAXBuilder;
import org.jdom2.output.XMLOutputter;
public class CopyOfJDomParse2 {
public CopyOfJDomParse2() {
//String xmlpath = "E:\\myNewDev\\updateAgent_121430\\CODE\\csp\\moss-ivm-ius-agent\\conf\\fileFilterList.xml";
String xmlpath = "D:\\fileFilterList.xml";
SAXBuilder builder = new SAXBuilder();
try {
Document doc = builder.build(xmlpath);
Element filesName = doc.getRootElement();
System.out.println(filesName);
// //注意此处取出的是root节点下面的一层的Element集合
List fileList = filesName.getChildren("files");
System.out.println("fileListSize "+ fileList.size());
for(int i=0;i<fileList.size();i++){
Element files = (Element)fileList.get(i);
String type = files.getAttributeValue("type");
System.out.println(type);
Element typeElmt = null;
String typeName = null;
if (type.equals("type1")) {
// String name1 = book.getChildTextTrim("file");
List<Element> nameList = files.getChildren("file");
System.out.println("nameList " + nameList);
System.out.println("nameListSize " + nameList.size());
for(int j=0;j<nameList.size();j++){
typeElmt = (Element)nameList.get(j);
System.out.println(typeElmt.getText());
}
}
}
// XMLOutputter outputter = new XMLOutputter();
// outputter.output(doc, new FileOutputStream(xmlpath));
} catch (JDOMException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
new CopyOfJDomParse2();
}
}
//对应的xml文件
<p><?xml version="1.0" encoding="GB2312" ?>
<FileList>
<!--1-->
<files type="type1">
<file>aaa</file>
<file>bbb</file>
</files>
<!--2-->
<files type="type2">
<file>ccc</file>
</files></p><p> <!--3-->
<files type="type3">
</files>
</FileList></p>