官方地址:http://www.dom4j.org/dom4j-1.6.1/guide.html
Dom4j 快速入门
Parsing XML (xml 解析)
以下例子演示了如何使用SAX解析器解析XML,返回一个DOM 模型的对象,即DOCUMENT.
有了DOCUMENT我们就可以进行文档操作了。
import java.net.URL; import org.dom4j.Document; import org.dom4j.DocumentException; import org.dom4j.io.SAXReader; public class Foo { public Document parse(URL url) throws DocumentException { // 以DOM4J默认的SAX解析器解析 SAXReader reader = new SAXReader(); // read函数的形参可以是url 也可以是 File类型,也可以是STRING类型的相对或绝对路径 Document document = reader.read(url); return document; } } Using Iterators(使用迭代器) 该部分演示了如何使用迭代器(迭代器是一种设计模式,可用于遍历如集合、数组等)进行文档的遍历。以下演示了获得三种的迭代器。 public void bar(Document document) throws DocumentException { // 获得根节点 Element root = document.getRootElement(); // i为根节点孩子节点的迭代器 for ( Iterator i = root.elementIterator(); i.hasNext(); ) { Element element = (Element) i.next(); // do something System.out.println(element.getName()); } // 名为“student1”节点以下孩子节点的迭代器 for ( Iterator i = root.elementIterator("student1" ); i.hasNext(); ) { Element foo = (Element) i.next(); // do something System.out.println(foo.getText()); } // 根节点属性的迭代器 for ( Iterator i = root.attributeIterator(); i.hasNext(); ) { Attribute attribute = (Attribute) i.next(); // do something System.out.println(attribute.getValue()); } }
————————————————————————————————————————
以下是:foo.xml
<?xml version="1.0" encoding="gb2312"?> <foo id="1111" fooname="test"> <student sn="01"><name>张三</name><age>18</age></student> <student sn="02"><name>李四</name><age>20</age></student> <student1 sn="03">小翁</student1> </foo>
————————————————————————————————————————
Main函数中执行如下命令:
Foo foo = new Foo(); Document doc ; //1.2 Using Iterators File file = new File("foo.xml"); try { //parse 为以上1.1 部分的方法 doc = foo.parse(file); foo.bar(doc); } catch (DocumentException e) { // TODO Auto-generated catch block e.printStackTrace(); }
结果:
student
student
student1
小翁
1111
test
Powerful Navigation with Xpath(使用Xpth进行导航)
XPath 使用路径表达式来选取 XML 文档中的节点或节点集。
具体可以参见http://www.w3school.com.cn/xpath/xpath_syntax.asp
注意:使用XPATH进行导航时,有时需要导入一个名jaxen-XXX.jar的包,该包可以在 官方DOM4J文件夹lib目录下有。
Dom4j XPath 表达式也以表示文档或文档树中的节点(如属性,元素,以及处理指令)。可以用一行简单的代码进行复杂的文档遍历。如下:
public void barWithXPath(Document document) { // “//”表示任意路径节点 如 //name 任意名为name 的节点 List<Node> list = document.selectNodes("//name"); for (Node nodeTmp : list) { System.out.println(nodeTmp.getText()); } //"//foo/student[2]" 表示带有foo路径下第二个student节点 Node node = document.selectSingleNode("//foo/student[2]"); // “@”表示属性 String name = node.valueOf("@sn"); System.out.println(name); }
————————————————————-
以下是:foo.xml
<?xml version="1.0" encoding="gb2312"?> <foo id="1111" fooname="test"> <student sn="01"><name>张三</name><age>18</age></student> <student sn="02"><name>李四</name><age>20</age></student> <student1 sn="03">小翁</student1> </foo>
————————————————————————————————————————
Main函数中执行如下命令:
Foo foo = new Foo(); Document doc ; //1.3 Powerful Navigation with Xpath File file = new File("foo.xml"); try { doc = foo.parse(file); foo.barWithXPath(doc); } catch (DocumentException e) { // TODO Auto-generated catch block e.printStackTrace(); }
结果:
张三
李四
02
例如,如果你想获取一个XHTML中的所有超级链接,可以采用如下方式:
public void findLinks(Document document) throws DocumentException { List list = document.selectNodes( "//a/@href" ); for (Iterator iter = list.iterator(); iter.hasNext(); ) { Attribute attribute = (Attribute) iter.next(); String url = attribute.getValue(); } }
—————————————————————–
MyXhtml.xhtml文件
<?xml version="1.0" encoding="UTF-8"?> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> <head> <title>MyXhtml.xhtml</title> </head> <body> <a href="1">www.oseschool.com</a> <a href="2">2222</a> <a href="3">3333</a> </body> </html>
—————————————————————–
注意:若要利用上述findLinks 函数得到MyXhtml.xhtml文件中的a标签中href的属性值,必须对代码进行一定的修改。主要是因为MyXhtml.xhtml文件中带有命名空间。
具体代码如下:
public Document parseWithNameSpace(File file) throws DocumentException { SAXReader reader = new SAXReader(); Map map = new HashMap(); //把文件中的所以命名空间先放入一个MAP中 map.put("xmlns1", "http://www.w3.org/1999/xhtml"); //设置命名空间 reader.getDocumentFactory().setXPathNamespaceURIs(map); Document document = reader.read(file); return document; } public void findLinks(Document document) throws DocumentException { //注意对要遍历的元素要加命名空间限制 List list = document.selectNodes("//xmlns1:a/@href"); for (Iterator iter = list.iterator(); iter.hasNext();) { Attribute attribute = (Attribute) iter.next(); String url = attribute.getValue(); System.out.println(url); } }
————————————————————————————————————————
Main函数执行:
Foo foo = new Foo(); Document doc ; //1.3 Powerful Navigation with Xpath File file = new File("MyXhtml.xhtml"); try { doc = foo.parseWithNameSpace(file); foo.findLinks(doc); } catch (DocumentException e) { // TODO Auto-generated catch block e.printStackTrace(); }
结果:
www.oseschool.com
2
3
Fast Looping(快速循环)
如果你要遍历一个较大的XML文档,那么我们推荐你使用快速循环(递归)方法,这样将避免创建迭代器对象带来的开销。如下:
public void treeWalk(Document document) { treeWalk( document.getRootElement() ); } //采用递归的方式 public void treeWalk(Element element) { for ( int i = 0, size = element.nodeCount(); i < size; i++ ) { Node node = element.node(i); //判断是否是元素,如<test>11</test>即为元素 if ( node instanceof Element ) { treeWalk( (Element) node ); } else { // do something....打印元素中的文本内容 System.out.println(node.getText()); } } }
————————————————————-
以下是:foo.xml
<?xml version="1.0" encoding="gb2312"?> <foo id="1111" fooname="test"> <student sn="01"><name>张三</name><age>18</age></student> </foo>
————————————————————————————————————————
Main函数执行:
Foo foo = new Foo(); Document doc ; //1.4 Fast Looping File file = new File("foo.xml"); try { //parse方法为1.1 中 parse方法 doc = foo.parse(file); foo.treeWalk(doc); } catch (DocumentException e) { // TODO Auto-generated catch block e.printStackTrace(); }
结果:
(空行)
(空行)
张三
18
分析:“(空行)”表示本行内容为空,或许很多人感到疑问,为什么会有两个空行了,由于
<foo id="1111" fooname="test"> <student sn="01"><name>张三</name><age>18</age></student> </foo>
在
<foo id="1111" fooname="test"><student sn="01"><name>张三</name><age>18</age></student></foo>
所以节点在同一行,结果就不会有空行。
————————————————————————————————————————
Creating a new XML document(创建一个新的XML文档) import org.dom4j.Document; import org.dom4j.DocumentHelper; import org.dom4j.Element; public class Foo { public Document createDocument() { Document document = DocumentHelper.createDocument(); Element root = document.addElement( "root" ); Element author1 = root.addElement( "author" ) .addAttribute( "name", "James" ) .addAttribute( "location", "UK" ) .addText( "James Strachan" ); Element author2 = root.addElement( "author" ) .addAttribute( "name", "Bob" ) .addAttribute( "location", "US" ) .addText( "Bob McWhirter" ); return document; } }
Writing a document to a file(写入一个文档到一个文件)
一种快速而简单地把文档写入到一个文件,即调用字符输出流的write方法。
FileWriter out = new FileWriter( "foo.xml" ); document.write( out );
如果你想要改变输出的格式,如宽松或紧凑的格式,而且你想要使用一些基本的字节或字符输出流,那么你可以使用XMLWriter类,如下。
import org.dom4j.Document; import org.dom4j.io.OutputFormat; import org.dom4j.io.XMLWriter; public class Foo { public void write(Document document) throws IOException { // lets write to a file XMLWriter writer = new XMLWriter( new FileWriter( "output.xml" ) ); writer.write( document ); writer.close(); // 打印出Pretty的样式。即元素之间有换行。 OutputFormat format = OutputFormat.createPrettyPrint(); writer = new XMLWriter( System.out, format ); writer.write( document ); // 紧凑的格式,所有元素在一行 format = OutputFormat.createCompactFormat(); writer = new XMLWriter( System.out, format ); writer.write( document ); } }
注意:如果按上述形式打印输出,是以计算机默认编码,进行写入操作,也就是如果在中文系统下,你读出的DOM,如果是UTF-8编码的,不会正确输出。所以建议用对上面的代码改进,如下:
OutputFormat outFmt=new OutputFormat(); outFmt.setEncoding("utf8"); try { XMLWriter xmlWriter=new XMLWriter(new FileOutputStream("dom4jtest.xml"),outFmt); xmlWriter.write(doc); xmlWriter.flush(); xmlWriter.close(); }
上面最大改变是把FileWriter->FileOutputStream.然后使用OutputFormat设定编码。
Converting to and from Strings(转换字符串)
如果你有一个文档对象的引用或任何其他像属性或元素的节点,那么你可以把他们转换为一种默认的XML文本,通过调用 asXML 方法。
Document document = ...; String text = document.asXML();
如果你有些XML的文本字符串,你可以把它再转换回文档对象,通过使用帮助方法DocumentHelper.parseText()
String text = "<person> <name>James</name> </person>"; Document document = DocumentHelper.parseText(text); Styling a Document with XSLT(使用XSLT格式一个文档)
要想在一个文档对象上运用一个XSLT可以直接调用SUN 的JAXP API(JAVA API FOR XML PROGRAM)。允许使用像Xalan或SAXON这样的任何XSLT引擎。这里有一个使用JAXP来创建transformer对象然后将XSLT运用在一个文档上。
import javax.xml.transform.Transformer; import javax.xml.transform.TransformerFactory; import org.dom4j.Document; import org.dom4j.io.DocumentResult; import org.dom4j.io.DocumentSource; public class Foo { public Document styleDocument( Document document, String stylesheet ) throws Exception { // load the transformer using JAXP TransformerFactory factory = TransformerFactory.newInstance(); Transformer transformer = factory.newTransformer( new StreamSource( stylesheet ) ); // now lets style the given document DocumentSource source = new DocumentSource( document ); DocumentResult result = new DocumentResult(); transformer.transform( source, result ); // return the transformed document Document transformedDoc = result.getDocument(); return transformedDoc; } }
———————————————————————————————————————-
Catalog.XML
<?xml version="1.0" encoding="ISO-8859-1"?> <catalog> <cd> <title>Empire Burlesque</title> <artist>Bob Dylan</artist> <country>USA</country> <company>Columbia</company> <price>10.90</price> <year>1985</year> </cd> </catalog>
———————————————————————————————————————
<?xml version="1.0" encoding="ISO-8859-1"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:template match="/"> <html> <body> <h2>My CD Collection</h2> <table border="1"> <tr bgcolor="#9acd32"> <th align="left">Title</th> <th align="left">Artist</th> </tr> <xsl:for-each select="catalog/cd"> <tr> <td><xsl:value-of select="title"/></td> <td><xsl:value-of select="artist"/></td> </tr> </xsl:for-each> </table> </body> </html> </xsl:template> </xsl:stylesheet>
———————————————————————————————————————
Main函数:
Foo foo = new Foo(); Document doc ; //1.4 Fast Looping File file = new File("catalog.xml"); try { doc = foo.parse(file); Document newDoc = foo.styleDocument(doc, "catalog.xsl"); // 1.6 中的write方法 foo.write(newDoc); } catch (DocumentException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); }
———————————————————————————————————————
结果:
<?xml version="1.0" encoding="UTF-8"?> <html> <body> <h2>My CD Collection</h2> <table border="1"> <tr bgcolor="#9acd32"> <th align="left">Title</th> <th align="left">Artist</th> </tr> <tr> <td>Empire Burlesque</td> <td>Bob Dylan</td> </tr> </table> </body> </html> <?xml version="1.0" encoding="UTF-8"?> <html><body><h2>My CD Collection</h2><table border="1"><tr bgcolor="#9acd32"><th align="left">Title</th><th align="left">Artist</th></tr><tr><td>Empire Burlesque</td><td>Bob Dylan</td></tr></table></body></html>
分析:结果中有一个为Pretty的样式,一个为compact的样式。还生成了一个output.xml
0 Responses
Stay in touch with the conversation, subscribe to the RSS feed for comments on this post.