- 浏览: 6613 次
- 性别:
- 来自: 北京
最新评论
自己写的一个用DOM方式处理xml的的工具类
最近没事整理了下关于java dom的应用,包含的dom方式的解析、创建、修改、删除等操作。感觉应该是能给初学dom的同学们提供点参考。
在写这个工具类的过程中我也发现了一些问题:比如要查找某个node节点下nodeName为version的子节点,是没有getElementByTagName方法的,很不方便,以致要修改某节点的内容的话,程序会写的很麻烦;还有一个问题就是,我删除了一个node节点后,在xml文档中,以前节点的位置成为了空行,这个空行我不知道怎么删除掉。
能帮我解决这两个问题的朋友欢迎给我回帖!
package com.yansirliu.common.xml; import java.io.File; import java.text.SimpleDateFormat; import java.util.Date; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.transform.Result; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerFactory; import javax.xml.transform.dom.DOMSource; import javax.xml.transform.stream.StreamResult; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.NamedNodeMap; import org.w3c.dom.Node; import org.w3c.dom.NodeList; /** * 用org.w3c.dom来处理xml文件 * * 本类中的transformXML(file)方法,可以在解析一切xml文件,并在控制台打印出来 * * @author yansirliu Mar 22, 201011:17:56 PM declaration: * */ public class XMLDomUtil { /** * 创建xml文档 */ public void createXML(File file) throws Exception { // 解析器工厂类 DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory .newInstance(); // 忽略空格 documentBuilderFactory.setIgnoringElementContentWhitespace(true); // 解析器 DocumentBuilder builder = documentBuilderFactory.newDocumentBuilder(); // xml对象 Document doc = builder.newDocument(); // 设置xml版本 doc.setXmlVersion("1.0"); // 创建根节点 Element root = doc.createElement("books"); // 为根节点添加属性 root.setAttribute("type", "编程类"); root.setAttribute("year", "2010"); // 将根节点添加到document中去,root添加到doc中去后,后面再向root中添加子节点,对与doc同样生效 doc.appendChild(root); /* 设置第一本书 */ Element bookElement = doc.createElement("book"); // 设置book节点的id属性 bookElement.setAttribute("id", "001"); // 设置name节点 Element nameElement = doc.createElement("name"); // 给method设置值 nameElement.setTextContent("java编程思想"); // 将method节点添加到page节点 bookElement.appendChild(nameElement); // 创建company节点 Element companyElement = doc.createElement("company"); companyElement.setTextContent("清华大学出版社"); bookElement.appendChild(companyElement); // 创建price节点 Element priceElement = doc.createElement("price"); priceElement.setTextContent("58.9"); bookElement.appendChild(priceElement); // 将第一本书添加到根节点 root.appendChild(bookElement); /* 设置第二本书 */ Element bookElement2 = doc.createElement("book"); // 设置book节点的id属性 bookElement2.setAttribute("id", "002"); // name节点 Element nameElement2 = doc.createElement("name"); nameElement2.setTextContent("JavaScript高级编程"); bookElement2.appendChild(nameElement2); // company节点 Element companyElement2 = doc.createElement("company"); companyElement2.setTextContent("北京理工大学出版社"); bookElement2.appendChild(companyElement2); // price节点 Element priceElement2 = doc.createElement("price"); priceElement2.setTextContent("66.5"); bookElement2.appendChild(priceElement2); // 加到root节点 root.appendChild(bookElement2); //保存 this.saveDocument(doc, file); } /** * 解析整个xml并打印出来 * * @param filePath */ public void transformXML(File file) throws Exception { Document doc = this.getDocument(file); // 取出根节点 Element root = doc.getDocumentElement(); // 解析打印该节点及所有子节点 this.transformNode(root, ""); } /** * 为已有的xml文档增加节点 * @param filePath */ public void addNode(File file) throws Exception{ //得到已有的book.xml对象,为其增加几个节点 Document doc = this.getDocument(file); //根节点 Element root = doc.getDocumentElement(); //先为已经有的两个book节点添加version节点 NodeList list = root.getElementsByTagName("name"); //java编程思想为第一版 Element version = doc.createElement("version"); version.setTextContent("第一版"); //JavaScript高级编程为第四版 Element version2 = doc.createElement("version"); version2.setTextContent("第二版"); //为book节点增加version节点 int length = list.getLength(); for(int i=0;i<length;i++){ Node node = list.item(i); if (node.getTextContent().trim().equals("java编程思想".trim())) { node.getParentNode().appendChild(version); }else if (node.getTextContent().trim().equals("JavaScript高级编程".trim())) { node.getParentNode().appendChild(version2); } } //新增一个book节点 Element book = doc.createElement("book"); book.setAttribute("id", "003"); Element name = doc.createElement("name"); name.setTextContent("ExtJS入门教程"); Element company = doc.createElement("company"); company.setTextContent("机械工业出版社"); Element price = doc.createElement("price"); price.setTextContent("34.5"); Element version3 = doc.createElement("version"); version3.setTextContent("第一版"); book.appendChild(name); book.appendChild(company); book.appendChild(price); book.appendChild(version3); root.appendChild(book); //保存 this.saveDocument(doc, file); } /** * 修改节点 * 我靠,dom方式的修改真的是很麻烦 * @param file * @throws Exception */ public void modifyNode(File file) throws Exception{ /* *将java的售价提高5元,JavaScript减少2元,ExtJS增加11.5元 */ Document doc = this.getDocument(file); //先取得所有NodeName为name的节点 NodeList nameList = doc.getElementsByTagName("name"); int length = nameList.getLength(); //为了尽量减少循环设此变量 int count = 0; //循环判断 for(int i=0;i<length && count < 3;i++){ Node node = nameList.item(i); if(node.getTextContent().trim().equals("java编程思想".trim())){ node = node.getParentNode(); node = node.getLastChild(); //当node节点不为空且node名称不为price时,不停向上面一个节点查找,直到上面在也没有节点 while(node != null && !node.getNodeName().equals("price")){ node = node.getPreviousSibling(); } if(node!=null && node.getNodeName().trim().equals("price".trim())){ String sPrice = this.getString(node.getTextContent()); double price = Double.parseDouble(sPrice); price = price + 5; node.setTextContent(new Double(price).toString()); } //修改完一本后记录数加一次 count++; } if(node.getTextContent().trim().equals("JavaScript高级编程".trim())){ node = node.getParentNode(); node = node.getLastChild(); while(node != null && !node.getNodeName().equals("price")){ node = node.getPreviousSibling(); } if(node!=null && node.getNodeName().trim().equals("price".trim())){ String sPrice = this.getString(node.getTextContent()); double price = Double.parseDouble(sPrice); price = price - 2; node.setTextContent(new Double(price).toString()); } //修改完一本后记录数加一次 count++; } if(node.getTextContent().trim().equals("ExtJS入门教程".trim())){ node = node.getParentNode(); node = node.getLastChild(); //当node节点不为空且node名称不为price时,不停向上面一个节点查找,直到上面在也没有节点 while(node != null && !node.getNodeName().equals("price")){ node = node.getPreviousSibling(); } if(node!=null && node.getNodeName().trim().equals("price".trim())){ String sPrice = this.getString(node.getTextContent()); double price = Double.parseDouble(sPrice); price = price + 11.5; node.setTextContent(new Double(price).toString()); } //修改完一本后记录数加一次 count++; } } this.saveDocument(doc, file); } /** * 删除node节点,当node被删除后,xml文件中会出现空行,我还不知道怎样去掉这些空行 * @param file * @throws Exception */ public void deleteNode(File file) throws Exception{ /* * 删除所有nodeName为verion的节点 */ Document doc = this.getDocument(file); NodeList list = doc.getElementsByTagName("version"); /* * NodeList特性:当其中包含的node被父节点删除后,NodeList也会随之将之删除,NodeList的length减少1,排序靠后的node会依次 * 向前移动,占据被移除的node的位置 * 下面循环中只要NodeList的长度还大于0,便继续循环,始终删除处于0位置的node */ for(int i=0;list.getLength()>0;){ Node node = list.item(i); node.getParentNode().removeChild(node); } this.saveDocument(doc, file); } /** * 递归方法,解析一个Node及其子Node并打印出来 * * @param Node * 要解析的的节点 * @param space * 第一个节点距离页面最左端的空格 * @throws Exception */ public void transformNode(Node node, String space) throws Exception { // 判断该Node对象是否为Element if (node.getNodeType() == Node.ELEMENT_NODE) { // 格式用空格,子节点头部与父节点相差几个空格 String addSpace = " "; // 先打印该节点名称及属性 String head = this.getNodeNameAndAttribute(node, space); System.out.print(head); // 判断该节点是否有ELEMENT_NODE类型子节点,如果再调用本方法递归 boolean check = this.checkChildNodes(node); if (check) { // 如果有子节点,则要换行显示了 System.out.println(); // 得到子节点 NodeList list = node.getChildNodes(); int length = list.getLength(); for (int i = 0; i < length; i++) { Node childNode = list.item(i); this.transformNode(childNode, space + addSpace); } } else { String content = node.getTextContent(); if (content.trim().length() > 0) { System.out.print(content); } } // 打印该节点的尾部信息,为了打印TextContent时没有多余的空格要进行判断 // 子节点校验为true时这样打印 if (check) { System.out.println(space + "<" + node.getNodeName() + "/>"); } // 子节点校验为false时这样打印 else { System.out.println("<" + node.getNodeName() + "/>"); } } } /** * 解析每个开始节点的名称及属性 * * @param node * 要解析的节点 * @param space * 子节点换行时加几个空格以助显示 * @return 该节点的xml方式显示 */ public String getNodeNameAndAttribute(Node node, String space) { StringBuffer buffer = new StringBuffer(); // 加入打头空格 buffer.append(space); // 节点名 buffer.append("<" + node.getNodeName()); // 解析根节点属性 if (node.hasAttributes()) { NamedNodeMap map = node.getAttributes(); for (int i = 0; i < map.getLength(); i++) { node = map.item(i); buffer.append(" " + node.getNodeName() + "=\"" + node.getNodeValue() + "\""); } buffer.append(">"); } else { buffer.append(">"); } return buffer.toString(); } /** * 判断一个节点是否含有最少一个ELEMENT_NODE类型的子节点 * * @param node * @return true表示该节点含有子节点且至少有一个子节点是ELEMENT_NODE类型的 * false表示该节点没有子节点或子节点全不是ELEMENT_NODE类型的 */ public boolean checkChildNodes(Node node) { boolean check = false; if (node.hasChildNodes()) { NodeList list = node.getChildNodes(); int length = list.getLength(); for (int i = 0; i < length && check == false; i++) { if (list.item(i).getNodeType() == Node.ELEMENT_NODE) { check = true; } } } return check; } /** * 过滤null、"null" * @param s * @return * @throws Exception */ public String getString(String s) throws Exception{ if(s == null || s.trim().equals("null") || s.trim().length()<1){ return ""; }else{ return s.trim().toString(); } } /** * 通过dom提供的document解析工厂得到document * @param file * @return * @throws Exception */ public Document getDocument(File file) throws Exception{ // 解析器工厂类 DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory .newInstance(); // 忽略空格 documentBuilderFactory.setIgnoringElementContentWhitespace(true); // 解析器 DocumentBuilder builder = documentBuilderFactory.newDocumentBuilder(); // xml对象 Document doc = builder.parse(file); return doc; } /** * 保存生成或修改完的xml文件 * @param doc * @param file * @throws Exception */ public void saveDocument(Document doc,File file) throws Exception{ // 开始把Document映射到文件 TransformerFactory transformerFactory = TransformerFactory .newInstance(); Transformer transformer = transformerFactory.newTransformer(); // 设置输出结果 DOMSource source = new DOMSource(doc); // 判断文件是否存在,如不存在则创建 if (!file.exists()) { file.createNewFile(); } // 设置输入源 Result xmlResult = new StreamResult(file); // 输出xml文件 transformer.transform(source, xmlResult); } /* * 在main方法中找到你自己存放xml文件的地址,把filepath修改下就可以了 */ public static void main(String[] args) throws Exception { // 获取工程的绝对路径 String projectRealPath = System.getProperties().getProperty("user.dir"); String xmlFoderPath = projectRealPath + "\\WebRoot\\xml"; String filePath = xmlFoderPath + "\\" + "book.xml"; File file = new File(filePath); //调用下面几个方法可以创建xml,添加节点,删除节点,修改内容,解析xml //new XMLDomUtil().createXML(file); //new XMLDomUtil().addNode(file); // new XMLDomUtil().deleteNode(file); //new XMLDomUtil().modifyNode(file); // new XMLDomUtil().transformXML(file); } }
附上用create方法生成的xml文件
<?xml version="1.0" encoding="UTF-8" standalone="no"?> <books type="编程类" year="2010"> <book id="001"> <name>java编程思想</name> <company>清华大学出版社</company> <price>58.9</price> </book> <book id="002"> <name>JavaScript高级编程</name> <company>北京理工大学出版社</company> <price>66.5</price> </book> </books>
相关推荐
自己写的一个dom4j解析xml文件工具类
分析这个项目可以帮助我们更深入地理解如何在实际开发中使用DOM4J和自定义工具类来处理XML数据。例如,我们可以看到如何加载XML文件,如何调用上述方法来获取所需信息,以及如何处理返回的结果。 总的来说,XML-DOM...
DOM4J是一个强大的Java库,专门用于处理XML文档。它提供了灵活、高性能的API,使得开发者可以方便地读取、写入、修改以及查询XML数据。DOM4J的名字来源于Document Object Model (DOM) 和 Java的结合,但它并不局限于...
在这个"dom4j工具类使用例子"中,我们将深入探讨如何利用DOM4J进行XML处理。 首先,`Dom4jUtil.java`可能是包含DOM4J实用方法的类。这个类可能包括了创建、查询、修改XML文档的各种静态方法。例如,可能会有用于...
在本教程中,我们将深入探讨如何使用DOM4J来解析XML文件,并创建一个无敌连环解析工具类。 首先,我们需要了解XML的基本概念。XML(可扩展标记语言)是一种标记语言,常用于数据交换和存储。它的结构化特性使其非常...
总结来说,`Dom4jUtils`工具类是DOM4J库的一个便利扩展,它提供了一系列便捷的方法来处理XML文件。在`MarkerIce.jar`这个特定的上下文中,`Dom4jUtils`可能用于XML配置的读取、解析和更新,从而简化了在Ice框架中的...
基于dom4j的读写xml文件的工具包。封装了dom4j操作xml文档的常和方法。 支持两种读写方法。1:针对小文件的读取整个文档,2:针对大文件的,逐行读取。读到几百M文件毫无压力。
本文将详细讲解如何使用Java实现XML到Map以及Map到XML的一键转换,并介绍一个已封装好的工具类`EasyXmlUtil`。 首先,XML到Map的转换涉及到XML的解析。在Java中,我们可以使用`javax.xml.parsers....
DOM4J是一个强大的Java库,专门用于处理XML文档。它提供了简单且高效的API来读取、写入、修改以及操作XML。在这个实例中,我们将深入理解DOM4J库如何帮助我们处理XML文档,并通过实际操作来熟悉其核心功能。 XML...
DOM4J是一个强大的Java XML API,它提供了全面的XML处理功能,包括解析、操作和生成XML文档。DOM4J在Java社区中被广泛使用,因其简洁的API和高效的性能而受到青睐。在这个文档中,我们将深入探讨DOM4J的核心概念和...
在处理XML时,DOM(Document Object Model)是一种常用的方法,它将XML文档解析为一个树形结构,使得我们可以方便地访问和修改XML文档的每一个部分。 DOM模型的核心是DOMDocument对象,它是整个XML文档的根节点,...
**DOM4J工具类详解** DOM4J是一个强大的Java XML处理库,它提供了一套灵活且功能丰富的API,使得在Java应用程序中解析、创建、修改XML文档变得异常简单。DOM4J的名字来源于“DOM for Java”,它是一个基于DOM模型的...
在IT行业中,代码重构是一项重要的技能,它有助于提高...总之,这次重构之旅旨在通过创建一个高效的XML工具类,提高代码的可复用性和性能。对于任何需要处理XML数据的Java开发者来说,这是一个值得学习和借鉴的案例。
本教程将详细介绍一个名为"WXML"的XML解析工具类,该工具类能便捷地将XML数据转换为Java对象,从而简化开发流程。 首先,XML解析分为两种主要方式:DOM(Document Object Model)和SAX(Simple API for XML)。DOM...
DOM4J是一个Java库,提供了更灵活和高效的XML处理功能,相比DOM,DOM4J提供了更丰富的API和更好的性能。它同样基于DOM模型,但提供了更友好的接口,适合处理大型XML文件。 3. **DOM4J解析步骤**: - 引入DOM4J库...
"Dom4j写XML和读取XML的工具类,非常好用" 这个标题表明我们要讨论的是一个使用Dom4j库来处理XML文档的Java工具类。Dom4j是一个非常流行的Java库,它提供了XML的解析、创建、修改以及查询功能,使得在Java中操作XML...
在提供的压缩包“xmlPro”中,可能包含了一系列示例代码或工具类,展示了如何集成XStream和DOM4J,以便在实际项目中高效地处理XML数据。 总的来说,理解和熟练掌握XStream和DOM4J对于Java开发人员来说非常重要,...
XML(eXtensible Markup Language)是一...总之,这个“XML解析工具类”是一个便捷的资源,提供了多种XML解析方式,适用于不同的场景和需求。不论你是初学者还是经验丰富的开发者,都能从中受益,更高效地处理XML数据。
这个工具类"XmlHandle"显然是为了方便开发者使用DOM4J来读取XML文件。 首先,DOM4J的核心概念包括Document、Element、Attribute、Namespace等。Document代表整个XML文档,Element是XML中的元素节点,Attribute表示...