sax是通过事件来解析xml的,它并不会像DOM一样直接一开始就把整个文档读入,而是解到哪,读到哪。这样,当目标xml文件很大的时候,也不会占用很多内存。 简单介绍一下几个主要事件,解析的时候一般就按下面的顺序执行 StartDocument:开始解析文档 StartElement:开始读取元素 characters:读取字符(就是元素内的内容) EndElement:读取元素结束 endDocument:文档解析结束 其实sax的原理很简单,当读到指定的位置时,触发相应的方法,我们就可以通过重写该方法来记录xml内的数据。 下面开始上实例,还是解析我博客的RSS,地址 http://www.pocketdigi.com/feed, 目标是读取文章标题 首先我们要先自定义一个类,继承DefaultHandler(sax的事件处理类),重写以上事件触发的方法:
package com.pocketdigi;
import java.util.ArrayList;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;
public class XmlHandler extends DefaultHandler {
String tempName;
//临时变量用于存储当前读取的标签
ArrayList temparr=new ArrayList();
//临时字符串数组用于存储读到的字符串
ArrayList titles=new ArrayList();
//存储读到的文章标题
boolean flag=false;
//因为博客名称跟标题的标签都是title,所以定时一个flag来区别是博客名称还是文章标题
@Override
public void characters(char[] ch, int start, int length)
throws SAXException {
// TODO Auto-generated method stub
super.characters(ch, start, length);
if(tempName.equals("title")&&flag){
temparr.add(new String(ch,start,length));
}
//当前标签是title,并且在item内时,把读到的字符转换成字符串存进临时数组
//之所以这样做,是回为当要读的标签内容过长时,characters方法不能一次把所有的字符都读进来,而是分多次读
}
@Override
public void endElement(String uri, String localName, String qName)
throws SAXException {
// TODO Auto-generated method stub
super.endElement(uri, localName, qName);
if(qName.equals("title")&&flag){
//title标签读取结束时,把temparr转换成string,存进titles
String title="";
for(int i=0;i
`然后在程序中调用:
package com.pocketdigi;
import java.io.StringReader;
import java.util.ArrayList;
import javax.xml.parsers.SAXParserFactory;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.util.EntityUtils;
import org.xml.sax.InputSource;
import org.xml.sax.XMLReader;
public class Main {
static ArrayList list;
public static void main(String[] args) {
// TODO Auto-generated method stub
String content=GetHtml("http://www.pocketdigi.com/feed");
//获取源码
SAXParserFactory factory = SAXParserFactory.newInstance();
try {
XMLReader reader = factory.newSAXParser().getXMLReader();
XmlHandler xmlhandler = new XmlHandler();
reader.setContentHandler(xmlhandler);
reader.parse(new InputSource(new StringReader(content)));
ArrayList titles=xmlhandler.titles;
for (String s:titles){
//循环输出标题
System.out.println(s);
}
}catch(Exception e){
e.printStackTrace();
}
}
//下载源码的方法
public static String GetHtml(String url){
try {
String html="";
HttpGet httpget=new HttpGet(url);
DefaultHttpClient httpclient=new DefaultHttpClient();
HttpResponse response=httpclient.execute(httpget);
if(response.getStatusLine().getStatusCode()==200){//如果状态码为200,就是正常返回
html=EntityUtils.toString(response.getEntity());
}
return html;
} catch (Exception e) {
// TODO Auto-generated catch block
return "error open url:" + url;
}
}
}`