Android解析XML的三种方式SAX、Pull、Dom

在android开发中,经常用到去解析xml文件,常见的解析xml的方式有一下三种:SAX、Pull、Dom解析方式。最近做了一个android版的CSDN阅读器,用到了其中的两种(sax,pull),本文对android解析xml的这三种方式进行一次总结。

今天解析的xml示例(channels.xml)如下:

<?xml version="1.0" encoding="utf-8"?>
<channel>
<item id="0" url="http://www.baidu.com">百度</item>
<item id="1" url="http://www.qq.com">腾讯</item>
<item id="2" url="http://www.sina.com.cn">新浪</item>
<item id="3" url="http://www.taobao.com">淘宝</item>
</channel>

 一、使用sax方式解析

 基础知识:

这种方式解析是一种基于事件驱动的api,有两个部分,解析器和事件处理器,解析器就是XMLReader接口,负责读取XML文档,和向事件处理器发送事件(也是事件源),事件处理器ContentHandler接口,负责对发送的事件响应和进行XML文档处理。

下面是ContentHandler接口的常用方法

public abstract void characters (char[] ch, int start, int length)

这个方法来接收字符块通知,解析器通过这个方法来报告字符数据块,解析器为了提高解析效率把读到的所有字符串放到一个字符数组(ch)中,作为参数传递给character的方法中,如果想获取本次事件中读取到的字符数据,需要使用start和length属性。

public abstract void startDocument () 接收文档开始的通知

public abstract void endDocument () 接收文档结束的通知

public abstract void startElement (String uri, String localName, String qName, Attributes atts) 接收文档开始的标签

public abstract void endElement (String uri, String localName, String qName) 接收文档结束的标签

在一般使用中为了简化开发,在org.xml.sax.helpers提供了一个DefaultHandler类,它实现了ContentHandler的方法,我们只想继承DefaultHandler方法即可。

另外SAX解析器提供了一个工厂类:SAXParserFactory,SAX的解析类为SAXParser 可以调用它的parser方法进行解析。

看了些基础以后开始上代码吧(核心代码,下载代码在附件)

public class SAXPraserHelper extends DefaultHandler {

 final int ITEM = 0x0005;

 List<channel> list;
 channel chann;
 int currentState = 0;

 public List<channel> getList() {
  return list;
 }

 /*
  * 接口字符块通知
*/
 @Override
 public void characters(char[] ch, int start, int length)
   throws SAXException {
  // TODO Auto-generated method stub
// super.characters(ch, start, length);
  String theString = String.valueOf(ch, start, length);
  if (currentState != 0) {
   chann.setName(theString);
   currentState = 0;
  }
  return;
 }

 /*
  * 接收文档结束通知
*/
 @Override
 public void endDocument() throws SAXException {
  // TODO Auto-generated method stub
  super.endDocument();
 }

 /*
  * 接收标签结束通知
*/
 @Override
 public void endElement(String uri, String localName, String qName)
   throws SAXException {
  // TODO Auto-generated method stub
  if (localName.equals("item"))
   list.add(chann);
 }

 /*
  * 文档开始通知
*/
 @Override
 public void startDocument() throws SAXException {
  // TODO Auto-generated method stub
  list = new ArrayList<channel>();
 }

 /*
  * 标签开始通知
*/
 @Override
 public void startElement(String uri, String localName, String qName,
   Attributes attributes) throws SAXException {
  // TODO Auto-generated method stub
  chann = new channel();
  if (localName.equals("item")) {
   for (int i = 0; i < attributes.getLength(); i++) {
    if (attributes.getLocalName(i).equals("id")) {
     chann.setId(attributes.getValue(i));
    } else if (attributes.getLocalName(i).equals("url")) {
     chann.setUrl(attributes.getValue(i));
    }
   }
   currentState = ITEM;
   return;
  }
  currentState = 0;
  return;
 }
}
private List<channel> getChannelList() throws ParserConfigurationException, SAXException, IOException
 {
  //实例化一个SAXParserFactory对象
  SAXParserFactory factory=SAXParserFactory.newInstance();
  SAXParser parser;
  //实例化SAXParser对象,创建XMLReader对象,解析器
  parser=factory.newSAXParser();
  XMLReader xmlReader=parser.getXMLReader();
  //实例化handler,事件处理器
  SAXPraserHelper helperHandler=new SAXPraserHelper();
  //解析器注册事件
  xmlReader.setContentHandler(helperHandler);
  //读取文件流
  InputStream stream=getResources().openRawResource(R.raw.channels);
  InputSource is=new InputSource(stream);
  //解析文件
  xmlReader.parse(is);
  return helperHandler.getList();
 }

从第二部分代码,可以看出使用SAX解析XML的步骤:

1、实例化一个工厂SAXParserFactory

2、实例化SAXPraser对象,创建XMLReader 解析器

3、实例化handler,处理器

4、解析器注册一个事件

4、读取文件流

5、解析文件

二、使用pull方式解析

基础知识:

在android系统中,很多资源文件中,很多都是xml格式,在android系统中解析这些xml的方式,是使用pul解析器进行解析的,它和sax解析一样(个人感觉要比sax简单点),也是采用事件驱动进行解析的,当pull解析器,开始解析之后,我们可以调用它的next()方法,来获取下一个解析事件(就是开始文档,结束文档,开始标签,结束标签),当处于某个元素时可以调用XmlPullParser的getAttributte()方法来获取属性的值,也可调用它的nextText()获取本节点的值。

其实以上描述,就是对整个解析步骤的一个描述,看看代码吧

private List<Map<String, String>> getData() {
  List<Map<String, String>> list = new ArrayList<Map<String, String>>();
  XmlResourceParser xrp = getResources().getXml(R.xml.channels);

  try {
   // 直到文档的结尾处
   while (xrp.getEventType() != XmlResourceParser.END_DOCUMENT) {
    // 如果遇到了开始标签
    if (xrp.getEventType() == XmlResourceParser.START_TAG) {
     String tagName = xrp.getName();// 获取标签的名字
     if (tagName.equals("item")) {
      Map<String, String> map = new HashMap<String, String>();
      String id = xrp.getAttributeValue(null, "id");// 通过属性名来获取属性值
      map.put("id", id);
      String url = xrp.getAttributeValue(1);// 通过属性索引来获取属性值
      map.put("url", url);
      map.put("name", xrp.nextText());
      list.add(map);
     }
    }
    xrp.next();// 获取解析下一个事件
   }
  } catch (XmlPullParserException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  } catch (IOException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  }

  return list;
 }

三、使用Dom方式解析

基础知识:

最后来看看Dom解析方式,这种方式解析自己之前也没有用过(在j2ee开发中比较常见,没有做过这方面的东西),在Dom解析的过程中,是先把dom全部文件读入到内存中,然后使用dom的api遍历所有数据,检索想要的数据,这种方式显然是一种比较消耗内存的方式,对于像手机这样的移动设备来讲,内存是非常有限的,所以对于比较大的XML文件,不推荐使用这种方式,但是Dom也有它的优点,它比较直观,在一些方面比SAX方式比较简单。在xml文档比较小的情况下也可以考虑使用dom方式。

Dom方式解析的核心代码如下:

public static List<channel> getChannelList(InputStream stream)
 {
  List<channel> list=new ArrayList<channel>();

  //得到 DocumentBuilderFactory 对象, 由该对象可以得到 DocumentBuilder 对象
  DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();

  try {
   //得到DocumentBuilder对象
   DocumentBuilder builder=factory.newDocumentBuilder();
   //得到代表整个xml的Document对象
   Document document=builder.parse(stream);
   //得到 "根节点"
   Element root=document.getDocumentElement();
   //获取根节点的所有items的节点
   NodeList items=root.getElementsByTagName("item");
   //遍历所有节点
   for(int i=0;i<items.getLength();i++)
   {
    channel chann=new channel();
    Element item=(Element)items.item(i);
    chann.setId(item.getAttribute("id"));
    chann.setUrl(item.getAttribute("url"));
    chann.setName(item.getFirstChild().getNodeValue());
    list.add(chann);
   }

  } catch (ParserConfigurationException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  } catch (SAXException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  } catch (IOException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  }

  return list;
 }

总结一下Dom解析的步骤(和sax类似)

1、调用 DocumentBuilderFactory.newInstance() 方法得到 DOM 解析器工厂类实例。

2、调用解析器工厂实例类的 newDocumentBuilder() 方法得到 DOM 解析器对象

3、调用 DOM 解析器对象的 parse() 方法解析 XML 文档得到代表整个文档的 Document 对象。

四、总结

除以上三种外还有很多解析xml的方法,比如DOM4J、JDOM等等。但其基本的解析方式包含两种,一种是事件驱动的(代表SAX),另一种方式是基于文档结构(代表DOM)。其他的只不过语法不一样而已。

源码下载:Android解析XML

原文地址:http://www.cnblogs.com/JerryWang1991

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • Android XmlPullParser 方式解析 Xml 文档

    Android XmlPullParser 方式解析 Xml 文档 xml 文件格式 <?xml version="1.0" encoding="UTF-8"?> <persons> <person id="1"> <name>张三</name> <age>22</age> </person> <person id="2"&g

  • Android中使用PULL方式解析XML文件深入介绍

    一.基本介绍 Android中极力推荐xmlpull方式解析xml. xmlpull不仅可用在Android上同样也适用于javase,但在javase环境中需自己获取xmlpull所依赖的类库,kxml2-2.3.0.jar,xmlpull_1_1_3_4c.jar. jar包下载网址 http://www.xmlpull.org/ http://kxml.sourceforge.net/ 二.例子 读取到xml的声明返回数字0 START_DOCUMENT; 读取到xml的结束返回数字1 E

  • Android基于Pull方式解析xml的方法详解

    本文实例讲述了Android基于Pull方式解析xml的方法.分享给大家供大家参考,具体如下: Pull解析和Sax解析很相似,都是轻量级的解析,在Android的内核中已经嵌入了Pull,所以我们不需要再添加第三方jar包来支持Pull. Pull解析和Sax解析不一样的地方有: (1)pull读取xml文件后触发相应的事件调用方法返回的是数字 (2)pull可以在程序中控制想解析到哪里就可以停止解析. 来看看实例: book.xml如下: <?xml version="1.0"

  • Android编程解析XML方法详解(SAX,DOM与PULL)

    本文实例讲述了Android编程解析XML方法.分享给大家供大家参考,具体如下: XML在各种开发中都广泛应用,Android也不例外.作为承载数据的一个重要角色,如何读写XML成为Android开发中一项重要的技能.今天就由我向大家介绍一下在Android平台下几种常见的XML解析和创建的方法. 在Android中,常见的XML解析器分别为SAX解析器.DOM解析器和PULL解析器,下面,我将一一向大家详细介绍. SAX解析器: SAX(Simple API for XML)解析器是一种基于事

  • Android编程使用pull方式解析xml格式文件的方法详解

    本文实例讲述了Android编程使用pull方式解析xml格式文件的方法.分享给大家供大家参考,具体如下: 上次已经说过使用Android sax解析xml,实际上还可以使用pull解析xml.这样的方式效率也是比较高的.pull不仅可以在Android上使用也可以用在javaee里面,需要的就是pull的jar包.这次的xml也使用上次的那个,如下所示 <?xml version="1.0" encoding="UTF-8"?> <persons

  • Android 使用Pull方法解析XML文件的方法

    Pull解析方法给应用程序完全的控制文档该怎么样被解析.Android中对Pull方法提供了支持的API,主要是 复制代码 代码如下: org.xmlpull.v1.XmlPullParser;org.xmlpull.v1.XmlPullParserFactory; 二个类,其中主要使用的是XmlPullParser,XmlPullParserFactory是一个工厂,用于构建XmlPullParser对象.应用程序通过调用XmlPullParser.next()等方法来产生Event,然后再处

  • Android中使用pull解析器操作xml文件的解决办法

    一.使用Pull解析器读取XML文件 除了可以使用SAX或DOM解析XML文件之外,大家也可以使用Android内置的Pull解析器解析XML文件. Pull解析器是一个开源的java项目,既可以用于android,也可以用于JavaEE.如果用在javaEE需要把其jar文件放入类路径中,因为Android已经集成进了Pull解析器,所以无需添加任何jar文件.android系统本身使用到的各种xml文件,其内部也是采用Pull解析器进行解析的. Pull解析器的运行方式与SAX 解析器相似.

  • Android使用Pull解析器解析xml文件的实现代码

    2个类:1个实体类Person.java,1个继承Activity的类 1.Person.java 复制代码 代码如下: package com.mrzhu.work_1_sax; public class Person { private String personId; private String name; private String address; private String tel; private String fax; private String email; publi

  • 详解Android之解析XML文件三种方式(DOM,PULL,SAX)

    1.xml文件代码 <?xml version="1.0" encoding="UTF-8" ?> <%@ page language="java" contentType="text/xml; charset=UTF-8" pageEncoding="UTF-8"%> <%@ taglib uri="http://java.sun.com/jsp/jstl/core

  • 实例解析Android中使用Pull解析器解析XML的方法

    1.Pull简介 Pull解析器是Android系统内置的的,Pull解析器与SAX解析器类似,他提供了类似的事件,如开始元素和介绍元素的事件,使用parser.next()可以进入下一个元素并触发相应的事件,然后进行相应的处理,当元素开始解析时,调用perser.nextText()方法就可以获取到下一个Text类型元素的值. 2.pull特点 (1)简单的结构,一个接口,一个另外,一个工厂组成了Pull解析器 (2)简单易用,Pull解析器只有一个重要的方法next(),他被用来检索下一个事

随机推荐