Android对XML文件解析
HTTP网络传输中的数据组织方式有三种方式:
1、HTML方式
2、XML方式
3、JSON方式
XML的结构解析如下:
1、节点
2、元素
3、属性和属性值
由于XML的扩展性强,致使它需要有稳定的基础规则来支持扩展,该语法规则是:
1、开始和结束标签匹配
2、嵌套标签不能互相嵌套
3、区分大小写
Android中,解析Xml数据的三种方式:
1、DOM(org.w3c.dom)
“文档对象模型”方式,解析完的Xml将生成一个树状结构的对象。
2、SAX(org.xml.sax)
Simple API for XML,以事件的形式通知程序,对Xml进行解析。
3、XMLPULL(org.xmlpull.v1)
类似于SAX方式,程序以“拉取”的方式对Xml进行解析。
SAX技术的介绍
SAX是一种以事件驱动的XML api,由它定义的事件流可以指定从解析器传到专门的处理程序的代码的XML结构,简单的讲,它解析速度快,占用内存少的解析器。这种解析器比较适合android 等移动设备。
使用SAX的优点是:
因为SAX的优势是流的方式处理,当遇到一个标签的时候,并不会记录下当前所碰到的标签。
也就是说,startEelment方法中,你所知道的信息,仅仅是当前的签名的名字和属性,至于标签的嵌套结构,上层标签的名字,是否有子元素与其他结构相关的信息,都是不知道的。
DOM技术的介绍
DOM是一种用于XML文档对象模型,可用于直接访问XML文档的各个部位,在DOM中文档被模拟为树状,其中XML语法的每一个组成部分都表示一个节点,DOM允许用户遍历文档树,从父节点移动到子节点和兄弟节点。并利用某节点类型特有的属性(元素具有属性,文本节点具有文本数据)
节点(XML文档中的每一个成分都是一个节点)
DOM是这样规定的:
整个文档是一个节点文档
每一个XML标签是一个元素节点
包含在XML元素中的文本是文本节点
每一个XML属性是一个属性节点
PULL技术的介绍
除了可以使用以上两种解析XML文件之外,我们也可以使用Java自带的PULL来解析XML文件。
PULL解析器的运行方式和sax解析器很相似,它提供了类似的事件。
如开始元素和结束元素,使用parser.next()可以进行下一个元素并且触发相应的事件,事件将作为代码被发送,因此可以使用一个switch来对事件进行选择,然后进行相应的处理。当开始解析元素时候,调用parser.nextText()方法可以获得下一个Text类型的元素。
PULL特点:
简单的结构:一个接口,一个例外,一个工厂组成的PULL解析器
简单易用:PULL解析器只有一个重要的方法next方法,他被用来检索下一个事件,而它只有5个常用的属性:
START DOCUMENT
START_TAG
TEXT
END_TAG
END_DOCUMENT
从内存占用率来说:
SAX和PULL比DOM占用的更少的内存解析方式,更加适合Android 手机开发。
下面举代码例子说明一下SAX的使用方法:
MyHandle.java
package com.sax.handler; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.jar.Attributes.Name; import org.xml.sax.Attributes; import org.xml.sax.SAXException; import org.xml.sax.helpers.DefaultHandler; public class MyHandler extends DefaultHandler { private HashMap<String, String> map = null;// 存储单个解析的完整对象 private List<HashMap<String, String>> list = null;// 存储所有的解析对象 private String currentTag = null;// 正在解析的元素的标签 private String currentValue = null;// 解析当前元素的值 private String nodeName = null;// 解析当前的节点名称 public MyHandler(String nodeName) { // TODO Auto-generated constructor stub this.nodeName = nodeName; } public List<HashMap<String, String>> getList() { return list; } @Override public void startDocument() throws SAXException { // TODO Auto-generated method stub // 当读到第一个开始标签的时候,会触发这个方法 list = new ArrayList<HashMap<String, String>>(); } @Override public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { // 当遇到文档的开头的时候,调用这个方法 if (qName.equals(nodeName)) { map = new HashMap<String, String>(); } if (attributes != null && map != null) { for (int i = 0; i < attributes.getLength(); i++) { map.put(attributes.getQName(i), attributes.getValue(i)); } } currentTag = qName; } @Override public void characters(char[] ch, int start, int length) throws SAXException { // TODO Auto-generated method stub // 这个方法是用来处理xml文件所读取到的内容 if (currentTag != null && map != null) { currentValue = new String(ch, start, length); if (currentValue != null && !currentValue.trim().equals("") && !currentValue.trim().equals("\n")) { map.put(currentTag, currentValue); } } currentTag = null;// 把当前的节点的对应的值和标签设置为空 currentValue = null; } @Override public void endElement(String uri, String localName, String qName) throws SAXException { // TODO Auto-generated method stub // 遇到结束标记的时候,会调用这个方法 if (qName.equals(nodeName)) { list.add(map); map = null; } super.endElement(uri, localName, qName); } }
SaxService.java
package com.sax.service;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import com.sax.handler.MyHandler;
public class SaxService {
public SaxService() {
// TODO Auto-generated constructor stub
}
public static List<HashMap<String, String>> readXML(
InputStream inputStream, String nodeName) {
try {
// 创建一个解析xml的工厂对象
SAXParserFactory spf = SAXParserFactory.newInstance();
SAXParser parser = spf.newSAXParser();// 解析xml
MyHandler handler = new MyHandler(nodeName);
parser.parse(inputStream, handler);
inputStream.close();
return handler.getList();
} catch (Exception e) {
// TODO: handle exception
}
return null;
}
}
HttpUtil.java
package com.sax.http;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
public class HttpUtils {
public HttpUtils() {
// TODO Auto-generated constructor stub
}
public static InputStream getXML(String path) {
InputStream inputStream = null;
try {
URL url = new URL(path);
if (url != null) {
HttpURLConnection connection = (HttpURLConnection) url
.openConnection();
connection.setConnectTimeout(3000);
connection.setDoInput(true);
connection.setRequestMethod("GET");
int code = connection.getResponseCode();
if (code == 200) {
inputStream = connection.getInputStream();
}
}
} catch (Exception e) {
// TODO: handle exception
}
return inputStream;
}
}
test.java ->main
package com.sax.test;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import com.sax.http.HttpUtils;
import com.sax.service.SaxService;
public class Test {
public Test() {
// TODO Auto-generated constructor stub
}
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path = "http://192.168.0.102:8080/myhttp/person.xml";
InputStream inputStream = HttpUtils.getXML(path);
try {
List<HashMap<String, String>> list = SaxService.readXML(
inputStream, "person");
for (HashMap<String, String> map : list) {
System.out.println(map.toString());
}
} catch (Exception e) {
// TODO: handle exception
}
}
}