您的位置:首页 > 移动开发 > Android开发

关于xml的解析在Android中的应用

2015-02-17 17:22 363 查看
Android技术中解析xml的方式一般都有三种,分别是SAX、DOM、Pull三种解析方式。其原理都是将xml文件转换成数据流来解析,但在细节上有分别存在着差别。
1.SAX技术是以事件为驱动的 xml API,由它定义的事件流可以从指定的解析器传到专门的处理程序代码的xml结构。其特点是解析速度快,占用内存少的解析器。主要有事件接口,即是文档的开始和结束标记,在其父类DefaulHandler中提供了这些方法的默认实现。其次是XMLReader为注册事件处理器并启动语法分析器,应用程序使用XMLReader。然后有InputSource即是读取文件。最后ContentHandler是最常用的SAX接口,因为它定义xml文档事件。其中代码中必须实现的几个方法分别为:



流程为文档开始——>元素开始——>元素文本获取——>元素结束——>文档结束。其中元素开始——>元素文本获取——>元素结束会遍历完所有的元素。
2.DOM解析技术是一种用于xml文档对象的模型,可用于直接访问xml文档的各个部分。在DOM中文档被模拟成树状,其中xml语法每个组成部分表示为一个节点。作为一apiDOM
允许用户遍历文档树,从父节点移动到子节点和兄弟节点等。通常DOM技术比SAX技术更容易掌握,因为他没有涉及到会带哦和复杂的状态管理,然而DOM实现常常是将所有的xml节点保持在内存中,降低效率。下面为树状图:



DOM基本的节点类型:Node:DOM的基本数据类型、Element:用户主要处理的对象、Attr:代表一个元素的属性、Text:一个Element或者Atrr的实际内容、Document:嗲表整个xml文档,一个Document通常被称为一棵DOM树。其中最为复杂的是节点之间的层次关系。主要用到DocumentBuilderFactory、DocumentBuilder、Document、Element、NodeList、getChildNodes()、getNodeType()等方法。
3.Pull是Android内置的解析器,其运行方式和SAX方式相似,提供类似的事件。如开始元素事件和结束元素事件。使用parser.next()方法可以进入到下一个元素触发相应的事件。当元素开始解析时调用parser.nextText()方法来获取下一个Text类型元素的值。
特点:
简单的结构:一个接口、一个例外、一个工厂组成pull解析器
简单易用:重要的方法是next(),用来检索下一个事件事件只有:START_DOCUMENT、START_TAG、TEXT、END_TAG、END_DOCUMENT几个事件。与SAX不同在于SAX的事件驱动是回调相应的方法。而Pull解析器并没有强制要求提供触发方法,应为他出发的不是一个方法,而是一个数字。
下面是一个例子分别用三种发发去解析xml文件。在服务器端写出一个News.xml文件



1.SAX解析代码:

import java.util.ArrayList;
import java.util.List;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

import cn.zxw.news.domain.NewInfo;

public class MyHandler extends DefaultHandler {
 private List<NewInfo> infos;// 存储所有对象
 private NewInfo info;// 存储一个完整节点为对象
 private String perTag;// 记录当前标签的值

 public List<NewInfo> getInfos() {
  return infos;
 }

 // 解析开始文档时会触发这个事件
 @Override
 public void startDocument() throws SAXException {
  System.out.println("文档加载开始");
  // infos初始化
  infos = new ArrayList<NewInfo>();

 }

 // 解析开始元素时会触发这个事件
 @Override
 public void startElement(String uri, String localName, String qName,
   Attributes attributes) throws SAXException {
  if ("newinfo".equals(localName)) {
   for (int i = 0; i < attributes.getLength(); i++) {
    info = new NewInfo();
    info.id = Integer.parseInt(attributes.getValue(i));

   }

  }
  perTag = localName;

 }

 // 读取文档时会触发该事件,用来处理xml文件所读到的内容
 @Override
 public void characters(char[] ch, int start, int length)
   throws SAXException {

  String data = new String(ch, start, length).trim();
  if (!"".equals(data.trim())) {
   // System.out.println("正在加载");

  }
  if ("title".equals(perTag)) {
   info.title = data;

  } else if ("content".equals(perTag)) {
   info.content = data;
  }
 }

 @Override
 public void endElement(String uri, String localName, String qName)
   throws SAXException {

  if ("newinfo".equals(localName)) {
   infos.add(info);
   info = null;

  }
  perTag = null;
 }

 @Override
 public void endDocument() throws SAXException {
  System.out.println("文档加载结束");
 }

}
2.DOM解析工具类
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import cn.zxw.news.domain.NewInfo;

public class DOMService {
 private static List<NewInfo> infos;
 private static NewInfo info;
 public static List<NewInfo> getNewInfos(InputStream inputStream)
   throws Exception {
  infos = new ArrayList<NewInfo>();
  DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
  DocumentBuilder builder = factory.newDocumentBuilder();
  Document document = builder.parse(inputStream);
  Element root = document.getDocumentElement();
  NodeList newInfoNodes = root.getElementsByTagName("newinfo");
  for (int i = 0; i < newInfoNodes.getLength(); i++) {
   Element element = (Element) newInfoNodes.item(i);
   info = new NewInfo();
   info.id = Integer.parseInt(element.getAttribute("id"));
   NodeList childNodeList = element.getChildNodes();
   for (int j = 0; j < childNodeList.getLength(); j++) {
    if (childNodeList.item(j).getNodeType() == Node.ELEMENT_NODE) {
     if ("title".equals(childNodeList.item(j).getNodeName())) {
      String title = childNodeList.item(j).getFirstChild()
        .getNodeValue();
      info.title = title;
     } else if ("content".equals(childNodeList.item(j)
       .getNodeName())) {
      String contetn = childNodeList.item(j).getFirstChild()
        .getNodeValue();
      info.content = contetn;

     }
    }
   }
   infos.add(info);
  }
  inputStream.close();

  return infos;

 }

}
3.Pull解析工具
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;

import org.xmlpull.v1.XmlPullParser;

import android.util.Xml;
import cn.zxw.news.domain.NewInfo;

public class PullXmlService {
 /**
  * 采用pull解析xml
  * @param inputStream
  * @return
  * @throws Exception
  */
 
 protected static List<NewInfo> getNewInfos(InputStream inputStream)
   throws Exception {
  List<NewInfo> infos = null;
  NewInfo info = null;
  XmlPullParser parser = Xml.newPullParser();
  parser.setInput(inputStream, "UTF-8");
  int eventType = parser.getEventType();
  while (eventType != XmlPullParser.END_DOCUMENT) {
   String name = parser.getName();
   switch (eventType) {
   case XmlPullParser.START_TAG:
    if ("newinfos".equals(name)) {
     infos = new ArrayList<NewInfo>();
    } else if ("newinfo".equals(name)) {
     info = new NewInfo();
     int id = Integer.parseInt(parser.getAttributeValue(0));
     info.id = id;
    } else if ("title".equals(name)) {
     String title = parser.nextText();
     info.title = title;
    } else if ("content".equals(name)) {
     String content = parser.nextText();
     info.content = content;
    }
    break;
   case XmlPullParser.END_TAG:
    if ("newinfo".equals(name)) {
     infos.add(info);
     info = null;
    }
    break;

   default:
    break;
   }
   eventType = parser.next();
  }
  return infos;
 }
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: