Javaweb-xml编程-sax解析与实例

来源:互联网 发布:数据质量提升方案 编辑:程序博客网 时间:2024/06/10 15:43

sax解析

使用sax的原因

  • 在使用DOM解析XML文档时,需要解读整个XML文档,在内存中的架构代表整个DOM树的document对象,从而再对XML进行操作;
  • 在以上的情况下,如果XML文档特别大,就会大量消耗计算机的内存,并且容易导致内存溢出;
  • SAX解析允许在读取文档的时候,即对文档进行处理,而不必等到整个文档装载完才对文档进行操作。

sax解析原理

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

  • 解析器可以使用JAXP的API创建,创建出SAX解析器后,就可以指定解析器去解析某个XML文档。
  • 解析器采用SAX方式在解析某个XML文档时,当它解析到XML文档的一个组成部分,就会去调用事件处理器的一个方法,将当前解析到的XML文件内容作为方法的参数传给事件处理器。
  • 事件处理器有程序员编写,程序员通过事件处理器中方法的参数,就可以很轻松地得到SAX解析器解析到的数据,从而决定如何对数据进行处理。

实例说明

xml文件

<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE 书架><书架>   <>         <书名 name="xxx">数据结构</书名>         <作者>严蔚敏</作者>         <售价>39.0元</售价>   </>   <>         <书名>大话设计模式</书名>         <作者>程杰</作者>         <售价>45.0</售价>   </></书架>

sax解析xml文档

代码①

package sax;import java.io.IOException;import javax.xml.parsers.ParserConfigurationException;import javax.xml.parsers.SAXParser;import javax.xml.parsers.SAXParserFactory;import org.xml.sax.Attributes;import org.xml.sax.ContentHandler;import org.xml.sax.Locator;import org.xml.sax.SAXException;import org.xml.sax.XMLReader;public class Demo1 {    public static void main(String[] args) throws ParserConfigurationException, SAXException, Exception {        //1.创建解析工厂        SAXParserFactory factory = SAXParserFactory.newInstance();        //2.得到解析器        SAXParser sp = factory.newSAXParser();        //3.得到读取器         XMLReader reader = sp.getXMLReader();        //4.设置内容处理器        reader.setContentHandler(new ListHandler());        //5.读取xml文档内容         reader.parse("src/MyXml.xml");    }}//处理器1:得到xml文档所有内容class ListHandler implements ContentHandler{    @Override    public void startElement(String uri, String localName, String name, Attributes atts) throws SAXException {        // TODO Auto-generated method stub        System.out.println("<"+ name +">");        //获取属性        for(int i = 0;i<atts.getLength();i++){            String attName = atts.getQName(i);            String attValue = atts.getValue(i);            System.out.println(attName +"="+ attValue);        }    }    @Override    public void endElement(String uri, String localName, String name) throws SAXException {        // TODO Auto-generated method stub        System.out.println("</"+name+">");    }    @Override    public void characters(char[] ch, int start, int length) throws SAXException {        // TODO Auto-generated method stub        System.out.println(new String(ch,start,length));    }    @Override    public void setDocumentLocator(Locator locator) {        // TODO Auto-generated method stub    }    @Override    public void startDocument() throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void endDocument() throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void startPrefixMapping(String prefix, String uri) throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void endPrefixMapping(String prefix) throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void ignorableWhitespace(char[] ch, int start, int length) throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void processingInstruction(String target, String data) throws SAXException {        // TODO Auto-generated method stub    }    @Override    public void skippedEntity(String name) throws SAXException {        // TODO Auto-generated method stub    }}

说明

  • 这是可以实现获取所有标签值的处理器1;
  • 处理器1的编写部分其实非常简单,只要实现ContentHandler,Ctrl+1,在我们需要用到的方法里填写需要的内容即可;
  • sax解析的五大步骤就是如上所示不变,处理器要编写我们需要的处理器内容。下面是就获取指定标签值编写处理器

代码②

package sax;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.XMLReader;import org.xml.sax.helpers.DefaultHandler;public class Demo2 {    public static void main(String[] args) throws ParserConfigurationException, SAXException, Exception {        //1.创建解析工厂        SAXParserFactory factory = SAXParserFactory.newInstance();        //2.得到解析器        SAXParser sp = factory.newSAXParser();        //3.得到读取器         XMLReader reader = sp.getXMLReader();        //4.设置内容处理器        reader.setContentHandler(new TagValueHandler());        //5.读取xml文档内容         reader.parse("src/MyXml.xml");    }}class TagValueHandler extends DefaultHandler{    private String currentTag;//记住当前解析到的是什么标签    private int needNumber = 2;//表示想获取第二个作者标签的值    private int currentNumber;//当前解析到的是第几个    @Override    public void startElement(String uri, String localName, String name, Attributes attributes) throws SAXException {        currentTag = name;        if(currentTag.equals("作者")){            currentNumber++;        }    }    @Override    public void characters(char[] ch, int start, int length) throws SAXException {        if("作者".equals(currentTag)&&currentNumber==needNumber){            System.out.println(new String(ch,start,length));        }    }    @Override    public void endElement(String uri, String localName, String name) throws SAXException {        currentTag = null;}}

说明

  • characters()方法用来处理内容
  • startElement()获取指定标签的值;
  • endElement()结束获取

代码③
最常用的处理器内容编写

package sax;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.XMLReader;import org.xml.sax.helpers.DefaultHandler;public class Demo3 {    @SuppressWarnings("unchecked")    public static void main(String[] args) throws ParserConfigurationException, SAXException, Exception {        //1.创建解析工厂        SAXParserFactory factory = SAXParserFactory.newInstance();        //2.得到解析器        SAXParser sp = factory.newSAXParser();        //3.得到读取器         XMLReader reader = sp.getXMLReader();        //4.设置内容处理器        BeanListHandler handler = new BeanListHandler();        reader.setContentHandler(handler);        //5.读取xml文档内容         reader.parse("src/MyXml.xml");         List<Book> list = handler.getBooks();//打断点不能有警告,需压制警告         System.out.println(list);    }}//把xml文档中的每一本书封装到一个book对象,并把多个book对象放在一个list集合中返回class BeanListHandler extends DefaultHandler{    private List list = new ArrayList();    private String currentTag;    private Book book;    @Override    public void startElement(String uri, String localName, String name, Attributes attributes) throws SAXException {        currentTag = name;        if("书".equals(currentTag)){            book = new Book();        }    }    @Override    public void characters(char[] ch, int start, int length) throws SAXException {        if("书名".equals(currentTag)){            String name = new String(ch,start,length);            book.setName(name);        }        if("作者".equals(currentTag)){            String author = new String(ch,start,length);            book.setAuthor(author);        }        if("售价".equals(currentTag)){            String price = new String(ch,start,length);            book.setPrice(price);        }           }    @Override    public void endElement(String uri, String localName, String name) throws SAXException {        if(name.equals("书")){            list.add(book);            book = null;        }        currentTag = null;//不加这句话会出现异常,使用断点异常跟踪异常根由    }    public List getBooks() {        return list;    }}

备注:传智播客视频学习笔记

原创粉丝点击