DOM,SAX,JDOM,DOM4J 四种方式解析xml

SAX

SAX采用事件处理的方式解析XML文件,利用 SAX 解析 XML 文档,涉及两个部分:解析器和事件处理器:

解析器:解析器可以使用JAXP(javax.xml.parsers)的API创建

事件处理器:SAX API中主要有四种处理事件的接口,它们分别是ContentHandler,DTDHandler, EntityResolver 和 ErrorHandler

特点:
1. 边读边解析,应用于大型XML文档
2. 只支持读
3. 访问效率低
4. 逐行扫描文件,顺序访问

示例

<?xml version="1.0" encoding="UTF-8"?>  
<books>  
    <book id="1">  
        <name>编程之美</name>  
        <price>34.0</price>  
        <author>《编程之美》小组</author>  
    </book>  
    <book id="2">  
        <name>平凡的世界</name>  
        <price>56.0</price>  
        <author>路遥</author>   
    </book>  
</books> 
package com.gz.xml;

/**
 * <br/>功能: 和xml对应的实体类
 * <br/>版本: 1.0
 */
public class Book {
    private String id;  
    private String name;  
    private String price;  
    private String author;  

    public String getId() {  
        return id;  
    }  
    public void setId(String id) {  
        this.id = id;  
    }  
    public String getName() {  
        return name;  
    }  
    public void setName(String name) {  
        this.name = name;  
    }  
    public String getPrice() {  
        return price;  
    }  
    public void setPrice(String price) {  
        this.price = price;  
    }  
    public String getAuthor() {  
        return author;  
    }  
    public void setAuthor(String author) {  
        this.author = author;  
    }  
}
package com.gz.xml;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

public class SAXXml {

    public static void main(String[] args) throws SAXException, IOException, ParserConfigurationException {
        SAXParserFactory saxpf = SAXParserFactory.newInstance(); 
        // 通过SAXParserFactory的实例获取SAXParser的实例  
        SAXParser parser = saxpf.newSAXParser();  
        MyHandler1 handler = new MyHandler1();
        parser.parse("src\\main\\resources\\books.xml", handler); 
        for (Book book : handler.getBooks()) {  
            System.out.println("书本id :" + book.getId());  
            System.out.println("书本名字 :" + book.getName());  
            System.out.println("书本价格 :" + book.getPrice());  
            System.out.println("书本作者 :" + book.getAuthor());  
            System.out.println("---------------------------------");  
        }  
    }
}
/**
 * <br/>功能: 事件处理器
 * <br/>版本: 1.0
 */
class MyHandler extends DefaultHandler {

    private List<Book> books;
    private Book book;
    private String tag;

    @Override
    public void startDocument() throws SAXException {
        super.startDocument();
        books = new ArrayList<Book>();
    }

    /**
     * @Description: TODO
     * @param uri 名称空间 URI,如果元素没有名称空间 URI,或者未执行名称空间处理,则为空字符串  
     * @param localName  本地名称(不带前缀),如果未执行名称空间处理,则为空字符串
     * @param qName 限定名(带有前缀),如果限定名不可用,则为空字符串
     * @param attributes 连接到元素上的属性。如果没有属性,则它将是空 Attributes 对象。在 startElement 返回后,此对象的值是未定义的
     */
    @Override
    public void startElement(String uri, String localName, String qName,
            Attributes attributes) throws SAXException {
        super.startElement(uri, localName, qName, attributes);
        tag=qName;
        if ("book".equals(qName)) {
            book=new Book();
            book.setId(attributes.getValue(0));
        }
    }

    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        super.endElement(uri, localName, qName);
        tag="";
        if ("book".equals(qName)) {
            books.add(book);
         }
    }

    @Override
    public void characters(char[] ch, int start, int length)
            throws SAXException {
        super.characters(ch, start, length);
        String string = new String(ch, start, length);
        if ("name".equals(tag)) {//判断当前内容,属于哪一个元素。
            book.setName(string);
        }else if ("price".equals(tag)) {
            book.setPrice(string);
        }else if ("author".equals(tag)) {
            book.setAuthor(string);
        }
    }

    public List<Book> getBooks() {
        return books;
    }

    public void setBooks(List<Book> books) {
        this.books = books;
    }

    public Book getBook() {
        return book;
    }

    public void setBook(Book book) {
        this.book = book;
    }
}

输出结果
书本id :1
书本名字 :编程之美
书本价格 :34.0
书本作者 :《编程之美》小组

书本id :2
书本名字 :平凡的世界
书本价格 :56.0
书本作者 :路遥

DOM

特点:
1. 解析器读入整个文档,然后构建一个驻留内存的树结构
2. 整个文档树在内存中,便于操作;支持删除、修改、重新排列等多种功能;访问效率高。

示例

package com.gz.xml;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import org.w3c.dom.Document;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

public class DomXml {

    public static void main(String[] args) throws ParserConfigurationException, SAXException, IOException {
        // 创建一个DocumentBuilderFactory对象  
        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();  
       // 创建一个DocumentBuilder对象  
        DocumentBuilder db = dbf.newDocumentBuilder();  
        // 通过DocumentBuilder对象的parse方法加载xml文件到当前项目  
        Document document = db.parse("src\\main\\resources\\books.xml"); 
        NodeList bookNodeList = document.getElementsByTagName("book"); 
        List<Book> bookList = new ArrayList<Book>();
        for(int i = 0;i < bookNodeList.getLength();i++) {
            Node bookNode = bookNodeList.item(i);
            Book book = new Book();

            // 得到book的属性
            NamedNodeMap bookNamedNodeMap = bookNode.getAttributes();
            for(int j = 0;j < bookNamedNodeMap.getLength();j++) {
                Node bookAttrNode = bookNamedNodeMap.item(j);
                String bookAttrName = bookAttrNode.getNodeName();
                if("id".equals(bookAttrName)) {
                    book.setId(bookAttrNode.getNodeValue());
                }
            }

             //解析book节点的子节点 
            NodeList bookChildNodeList = bookNode.getChildNodes();
            for(int z = 0;z < bookChildNodeList.getLength();z++) {
                if (bookChildNodeList.item(z).getNodeType() == Node.ELEMENT_NODE) {
                    Node bookChildNode = bookChildNodeList.item(z);
                    String bookChildNodeName = bookChildNode.getNodeName();
                    String bookChildNodeValue = bookChildNode.getFirstChild().getNodeValue();
                    if("name".equals(bookChildNodeName)) {
                        book.setName(bookChildNodeValue);
                    } else if("price".equals(bookChildNodeName)) {
                        book.setPrice(bookChildNodeValue);
                    } else if("author".equals(bookChildNodeName)) {
                        book.setAuthor(bookChildNodeValue);
                    } 
                }
            }
            bookList.add(book);
        }

        for(Book book : bookList) {
            System.out.println("书本id :" + book.getId());  
            System.out.println("书本名字 :" + book.getName());  
            System.out.println("书本价格 :" + book.getPrice());  
            System.out.println("书本作者 :" + book.getAuthor());  
            System.out.println(); 
        }
    }
}

输出结果
书本id :1
书本名字 :编程之美
书本价格 :34.0
书本作者 :《编程之美》小组

书本id :2
书本名字 :平凡的世界
书本价格 :56.0
书本作者 :路遥

备注: Node和Element的关系:
简单的说就是Node是一个基类,DOM中的Element,Text和Comment都继承于> > 它。 换句话说,Element,Text和Comment是三种特殊的Node,它们分别叫做ELEMENT_NODE, TEXT_NODE和COMMENT_NODE。
所以我们平时使用的html上的元素,即Element,是类型为ELEMENT_NODE的Node。

JDOM

特点:
JDOM
优点:①是基于树的处理XML的Java API,把树加载在内存中
②没有向下兼容的限制,因此比DOM简单
③速度快,缺陷少
④具有SAX的JAVA规则
缺点:①不能处理大于内存的文档
②JDOM表示XML文档逻辑模型。不能保证每个字节真正变换。
③针对实例文档不提供DTD与模式的任何实际模型。
④不支持与DOM中相应遍历包
最适合于:JDOM具有树的便利,也有SAX的JAVA规则。在需要平衡时使用

Jar包

<dependency>
    <groupId>jdom</groupId>
    <artifactId>jdom</artifactId>
    <version>1.0</version>
</dependency>

示例

package com.gz.xml;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import org.jdom.Document;
import org.jdom.Element;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;

public class JDOMXml {

    @SuppressWarnings("unchecked")
    public static void main(String[] args) {

        File f=new File("src\\main\\resources\\books.xml");    
        SAXBuilder builder=new SAXBuilder();  
        List<Book> bookList = new ArrayList<Book>();
        try {  
            Document doc=builder.build(new FileInputStream(f));  
            Element root=doc.getRootElement();  

            List<Element> list=root.getChildren("book");  
            for(int i=0;i<list.size();i++){  
                Element ele=(Element)list.get(i);  
                Book book = new Book();
                book.setId(ele.getAttribute("id").getValue());
                book.setName(ele.getChildText("name"));
                book.setPrice(ele.getChildText("price"));
                book.setAuthor(ele.getChildText("author"));
                bookList.add(book);
            }  
        } catch (FileNotFoundException e) {  
               e.printStackTrace();  
        } catch (JDOMException e) {  
               e.printStackTrace();  
        } catch (IOException e) {  
              e.printStackTrace();  
        }  

        for (Book book : bookList) {  
            System.out.println("书本id :" + book.getId());  
            System.out.println("书本名字 :" + book.getName());  
            System.out.println("书本价格 :" + book.getPrice());  
            System.out.println("书本作者 :" + book.getAuthor());  
            System.out.println();  
        } 
    }
}

输出结果
书本id :1
书本名字 :编程之美
书本价格 :34.0
书本作者 :《编程之美》小组

书本id :2
书本名字 :平凡的世界
书本价格 :56.0
书本作者 :路遥

DOM4J

特点:
DOM4J
具有性能优异、灵活性好、功能强大和极端易用的特点是一个开放源代码的软件

Jar包

<dependency>
     groupId>dom4j</groupId>
     <artifactId>dom4j</artifactId>
     <version>1.6.1</version>
</dependency>

示例

package com.gz.xml;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

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

public class DOM4JXml {

    @SuppressWarnings("unchecked")
    public static void main(String[] args) {
        SAXReader reader=new SAXReader();  
        List<Book> bookList = new ArrayList<Book>();
        try {  
          Document doc=reader.read(new FileInputStream(new File("src\\main\\resources\\books.xml")));  
          Element root=doc.getRootElement();  
          Iterator<Element> it=root.elementIterator();  
          while(it.hasNext()){  
              Element ele=(Element)it.next();  
              Book book = new Book();
              book.setId(ele.attributeValue("id"));
              book.setName(ele.elementText("name"));
              book.setPrice(ele.elementText("price"));
              book.setAuthor(ele.elementText("author"));
              bookList.add(book);
              System.out.println(ele.elementText("name")+"---"+ele.elementText("age"));  
          }  
        } catch (FileNotFoundException e) {  
          e.printStackTrace();  
        } catch (DocumentException e) {  
          e.printStackTrace();  
        }  

        for (Book book : bookList) {  
            System.out.println("书本id :" + book.getId());  
            System.out.println("书本名字 :" + book.getName());  
            System.out.println("书本价格 :" + book.getPrice());  
            System.out.println("书本作者 :" + book.getAuthor());  
            System.out.println();  
        } 

    }
}

输出结果
书本id :1
书本名字 :编程之美
书本价格 :34.0
书本作者 :《编程之美》小组

书本id :2
书本名字 :平凡的世界
书本价格 :56.0
书本作者 :路遥

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值