程序员我爱编程

xml解析中sax解析

2018-03-15  本文已影响44人  李霖神谷

xml解析中的sax解析:
1,工作方式:
逐步扫描xml文档,当遇到标签时触发解析处理器,通过事件处理的方式来解析xml。
2,优点:
不需要文件整个内容加载到内存,只需要逐步扫描一部分内容,通过方法处理数据。
缺点:
每次解析只能处理一次数据,要想重复处理只能再次加载。还有只能进行查询操作,不能进行增删改查操作。
3,代码的具体实现:
解析的xml文件:

<?xml version="1.0" encoding="gbk"?>
<书架>
    <书>
        <书名>西游记</书名>
        <作者>吴承恩</作者>
        <价格>188</价格>
    </书>
    <书>
        <书名>三国</书名>
        <作者>罗贯中</作者>
        <价格>188</价格>
    </书>

    <书>
        <书名>水浒传</书名>
        <作者>施耐庵</作者>
        <价格>188</价格>
    </书>
    
    <书>
        <书名>红楼梦</书名>
        <作者>曹雪芹</作者>
        <价格>188</价格>
    </书>
</书架>

3.1通过java对xml文件解析代码:


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 SaxJiexi {

    public static void main(String[] args) throws Exception{
        // TODO Auto-generated method stub
        //1.获取解析器工厂
        SAXParserFactory factor=SAXParserFactory.newInstance();
        //2.获取解析器
        SAXParser parser=factor.newSAXParser();
        //3.获取读取器
        XMLReader reader=parser.getXMLReader();
        //4.注册事件处理器,对读取到的标签进行处理。
        reader.setContentHandler(new MyContentHandler());
        //5.解析xml文件
        reader.parse("book.xml");
    }

}
class MyContentHandler implements ContentHandler{

    @Override
    
    public void setDocumentLocator(Locator locator) {
        // TODO Auto-generated method stub
        
    }

    @Override
    public void startDocument() throws SAXException {
        // TODO Auto-generated method stub
        System.out.println("文档解析开始了");
    }

    @Override
    public void endDocument() throws SAXException {
        // TODO Auto-generated method stub
        System.out.println("文档解析结束了");
    }

    @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 startElement(String uri, String localName, String qName,
            Attributes atts) throws SAXException {
        // TODO Auto-generated method stub
        System.out.println("发现了开始标签"+qName);
    }

    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        // TODO Auto-generated method stub
        System.out.println("发现了结束标签"+qName);
    }

    @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 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
        
    }
    
    
}

3.2上面的代码,通过创建myCtenthendler实现Ctenthendler接口来对解析到的数据进行处理,但是要想只对xml文件中某一个标签进行查询,就显得代码过于缀余。有一个类DefaultHandler实现了Ctenthendler中的所有的方法,不想使用的方法父类已经空实现了,想要实现的方法,可以覆盖父类的方法,这种设计模式,叫做适配器模式。

class MyContentHandler2 extends DefaultHandler{
    private String name=null;
    @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 startElement(String uri, String localName, String qName,
            Attributes attributes) throws SAXException {
        // TODO Auto-generated method stub
        this.name=qName;
        
    }
    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        // TODO Auto-generated method stub
        this.name=null;
    }
    @Override
    public void characters(char[] ch, int start, int length)
            throws SAXException {
        // TODO Auto-generated method stub
        if("书名".equals(name)){
            System.out.println(new String(ch,start,length));
        }
    }
}

上面代码,筛选书名内的标签体内容。解析器调用characters方法来报告字符数据的每个存储块。xml中的回车换行也属于标签体内容,所以这里再在endElement中将name设置为null;

上一篇下一篇

猜你喜欢

热点阅读