XML的SAX解析以及DOM解析和SAX解析区别

简介:

前言:

XML解析工具

DOM解析原理:
    1)JAXP (oracle-Sun公司官方)
    2)JDOM工具(非官方)
    3)Dom4J工具(非官方)
    三大框架(默认读取xml的工具就是Dom4j)
    .......

SAX解析原理:
    1)Sax解析工具(oracle-sun公司官方)

老样子,三个问题:

SAX解析是什么?
SAX怎么用?
SAX运用场景?

SAX是什么?

也是用来解析XML的
SAX解析工具- 内置在jdk中。org.xml.sax.*

SAX运用场景?

DOM解析原理:一次性把xml文档加载进内存,然后在内存中构建Document树。
对内存要求比较要。    
缺点: 不适合读取大容量的xml文件,容易导致内存溢出。

SAX解析原理: 加载一点,读取一点,处理一点。对内存要求比较低。

SAX解析工具核心:

核心的API:

SAXParser类: 用于读取和解析xml文件对象
parse(File f, DefaultHandler dh)方法: 解析xml文件

参数一: File:表示 读取的xml文件。

参数二: DefaultHandler: SAX事件处理程序。使用DefaultHandler的子类

第一步:创建对象

    //1.创建SAXParser对象
    SAXParser parser = SAXParserFactory.newInstance().newSAXParser();
        
        //2.调用parse方法
        /**
         * 参数一: xml文档
         * 参数二: DefaultHandler的子类   MyDefaultHandler()为自定义
         */
    parser.parse(new File(".\\src\\Go\\person.xml"),  
    new MyDefaultHandler());

注意:
这里创建SAXParser对象 不能直接通过构造函数来创造,因为用到了单例工厂模式。

链接:类 SAXParser的jdk文档

这里写图片描述
这里写图片描述
这里写图片描述
这里写图片描述

所以创建一个SAXParser对象 需要:
SAXParserFactory.newInstance().newSAXParser();

DefaultHandler类的API:后三个最重要

  1. void startDocument() : 在读到文档开始时调用
  1. void endDocument() :在读到文档结束时调用
  2. void startElement(String uri, String localName, String qName, Attributes attributes) :
    读到开始标签时调用
  3. void endElement(String uri, String localName, String qName) :读到结束标签时调用
  4. void characters(char[] ch, int start, int length) : 读到文本内容时调用

第二步:自定义类继承DefaultHandler重写方法

这些都是要重写的 举个例子:

public class MyDefaultHandler extends DefaultHandler {
    
    /**
     * 开始文档时调用
     */
    @Override
    public void startDocument() throws SAXException {
        System.out.println("MyDefaultHandler.startDocument()");
    }
    
    /**
     * 开始标签时调用
     * @param qName: 表示开始标签的标签名
     * @param attributes: 表示开始标签内包含的属性列表
     */
    @Override
    public void startElement(String uri, String localName, String qName,
            Attributes attributes) throws SAXException {
        System.out.println("MyDefaultHandler.startElement()-->"+qName);
    }
    
    /**
     * 结束标签时调用
     * @param qName: 结束标签的标签名称
     */
    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        System.out.println("MyDefaultHandler.endElement()-->"+qName);
    }
    
    /**
     * 读到文本内容的时调用
     * @param ch: 表示当前读完的所有文本内容
     * @param start: 表示当前文本内容的开始位置
     * @param length: 表示当前文本内容的长度
     * char[](                                       张三              20)   100
     *                              98 2   
     */ 
    @Override
    public void characters(char[] ch, int start, int length)
            throws SAXException {
        //得到当前文本内容
        String content = new String(ch,start,length);
        System.out.println("MyDefaultHandler.characters()-->"+content);
    }
    
    /**
     * 结束文档时调用
     */
    @Override
    public void endDocument() throws SAXException {
        System.out.println("MyDefaultHandler.endDocument()");
    }
    
}

xml样例:

<?xml version="1.0" encoding="utf-8"?>
<contactList>
    <contact id="001" name="eric">
        <name>张三</name>
        <age>20</age>
        <phone>134222223333</phone>
        <email>zhangsan@qq.com</email>
        <qq>432221111</qq>
    </contact>
    <contact id="002" name="jacky">
        <name>eric</name>
        <age>20</age>
        <phone>134222225555</phone>
        <email>lisi@qq.com</email>
        <qq>432222222</qq>
    </contact>
</contactList>

结果:

MyDefaultHandler.startDocument()
MyDefaultHandler.startElement()-->contactList
MyDefaultHandler.characters()-->
    
MyDefaultHandler.startElement()-->contact
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->name
MyDefaultHandler.characters()-->张三
MyDefaultHandler.endElement()-->name
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->age
MyDefaultHandler.characters()-->20
MyDefaultHandler.endElement()-->age
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->phone
MyDefaultHandler.characters()-->134222223333
MyDefaultHandler.endElement()-->phone
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->email
MyDefaultHandler.characters()-->zhangsan@qq.com
MyDefaultHandler.endElement()-->email
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->qq
MyDefaultHandler.characters()-->432221111
MyDefaultHandler.endElement()-->qq
MyDefaultHandler.characters()-->
    
MyDefaultHandler.endElement()-->contact
MyDefaultHandler.characters()-->
    
MyDefaultHandler.startElement()-->contact
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->name
MyDefaultHandler.characters()-->eric
MyDefaultHandler.endElement()-->name
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->age
MyDefaultHandler.characters()-->20
MyDefaultHandler.endElement()-->age
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->phone
MyDefaultHandler.characters()-->134222225555
MyDefaultHandler.endElement()-->phone
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->email
MyDefaultHandler.characters()-->lisi@qq.com
MyDefaultHandler.endElement()-->email
MyDefaultHandler.characters()-->
        
MyDefaultHandler.startElement()-->qq
MyDefaultHandler.characters()-->432222222
MyDefaultHandler.endElement()-->qq
MyDefaultHandler.characters()-->
    
MyDefaultHandler.endElement()-->contact
MyDefaultHandler.characters()-->

MyDefaultHandler.endElement()-->contactList
MyDefaultHandler.endDocument()

注意:
问题:MyDefaultHandler.characters()-->空白 ?

答:

    <contactList>
    <contact>
    之间也是有文本的 是换行和空格 被characters方法读取了。

来看一下SAX解析XML的流程图:(图片来自传智播客)
回到开头SAX解析原理: 加载一点,读取一点,处理一点。对内存要求比较低。
这里写图片描述


总结:

==================DOM解析 vs SAX解析 ============================

DOM解析 :

原理: 一次性加载xml文档,不适合大容量的文件读取
DOM解析可以任意进行增删改成
DOM解析任意读取任何位置的数据,甚至往回读
DOM解析面向对象的编程方法(Node,Element,Attribute),  
Java开发者编码比较简单。

SAX解析 :

原理: 加载一点,读取一点,处理一点。适合大容量文件的读取
SAX解析只能读取
SAX解析只能从上往下,按顺序读取,不能往回读
SAX解析基于事件的编程方法。java开发编码相对复杂。

XML操作:

            1)Dom4j修改xml文档
                 new XMLWrier();
                    ......
            2)xPath技术: 快速查询xml节点
                    selectNodes()
                    selectSinglNode();    
            3)  SAX解析
                    SAXParser parse
                        parser()
                DefaultHandler类:
                        startElement();
                        characters();
                        endElement();
目录
相关文章
|
25天前
|
前端开发 JavaScript 算法
深入理解前端框架:解析 React 的虚拟 DOM
虚拟 DOM 是 React 前端框架的核心概念之一。本文将深入探讨虚拟 DOM 的原理和应用,帮助读者更好地理解 React 框架的工作机制,并学习如何高效地使用虚拟 DOM 进行前端开发。
22 1
|
1天前
|
并行计算 API 计算机视觉
Python多线程与多进程:概念、区别及应用场景解析
Python多线程与多进程:概念、区别及应用场景解析
|
16天前
|
XML 存储 IDE
Java_XML解析精讲
Java_XML解析精讲
11 0
|
19天前
|
存储 缓存 JavaScript
|
22天前
|
XML 机器学习/深度学习 JSON
在火狐浏览器调ajax获取json数据时,控制台提示“XML 解析错误:格式不佳”。
在火狐浏览器调ajax获取json数据时,控制台提示“XML 解析错误:格式不佳”。
18 0
在火狐浏览器调ajax获取json数据时,控制台提示“XML 解析错误:格式不佳”。
|
1月前
|
XML Java 数据格式
Spring5源码(17)-Spring解析xml默认命名空间
Spring5源码(17)-Spring解析xml默认命名空间
18 0
|
1月前
|
XML JavaScript Java
Spring5源码(16)-Spring将Xml文件解析为Document对象
Spring5源码(16)-Spring将Xml文件解析为Document对象
27 0
|
1月前
|
缓存 负载均衡 网络协议
什么是云解析DNS和普通的DNS解析有何区别
什么是云解析DNS和普通的DNS解析有何区别
113 0
|
1月前
|
XML 存储 安全
Unity 数据读取|(五)XML文件解析(XmlDocument,XmlTextReader)
Unity 数据读取|(五)XML文件解析(XmlDocument,XmlTextReader)
|
1月前
|
XML JavaScript Java
JAVA XML 解析
XML (eXtensible Markup Language) 意为可扩展标记语言,被多数技术人员用以选择作为数据传输的载体,成为一种通用的数据交换格式,xml的平台无关性,语言无关性,系统无关性,给数据集成与交互带来了极大的便利。在不同的语言中,解析xml的方式都是一样的,只不过实现的语法不同而已。众所周知,现在解析XML的方法越来越多,但主流的方法也就四种,即:DOM、SAX、JDOM和DOM4J。

相关产品

  • 云迁移中心
  • 推荐镜像

    更多