Android 之xml解析
<?xml version="1.0" encoding="UTF-8"?>
<persons>
<person id="">
<name>jack</name>
<age></age>
</person>
<person id="">
<name>rose</name>
<age></age>
</person>
</persons>
Android中,常见的XML解析器分别为:
SAX解析器:SAX(org.xml.sax)Simple API for XML,以事件的形式通知程序,对Xml进行解析。
DOM解析器:DOM(org.w3c.dom)“文档对象模型”方式,解析完的Xml将生成一个树状结构的对象。(不推荐)
PULL解析器:XMLPULL(org.xmlpull.v1)类似于SAX方式,程序以“拉取”的方式对Xml进行解析。
---------------------
SAX解析器:是一种以事件驱动的XML api,由它定义的事件流可以指定从解析器传到专门的处理程序的代码的XML结构,
简单的讲,它解析速度快,占用内存少的解析器。这种解析器比较适合android 等移动设备。


1 定义变量:存储单个解析的完整对象HashMap<String, String> map
存储所有的解析对象 List<HashMap<String,String>> list
正在解析的元素的标签 String currentTag=null;
解析当前元素的值 String currentVal=null;
解析当前节点名称String nodeName=null;
并为list对象生成get方法和在构造方法中传递正在解析的节点名称
2.完成方法:
3.定义service 创建SAXParserFactory对象 SAXParser对象来解析xml,通过定义的list的get方法返回
4.定义http工具类 返回xml从服务器返回的输入流
5.建立测试类 指定网络路径
myHandler.java
package com.sax.handler; import java.util.ArrayList;
import java.util.HashMap;
import java.util.List; 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 currentVal=null;//解析当前元素的值
private String nodeName=null;//解析当前节点名称 public List<HashMap<String, String>> getList() {
return list;
} public myHandler(String nodeName) {
// TODO Auto-generated constructor stub
this.nodeName=nodeName;
} //解析到开始文档
//当读到第一个开始标签的时候会触发这个方法
@Override
public void startDocument() throws SAXException {
// TODO Auto-generated method stub
System.out.println("--startDocument()--");
list=new ArrayList<HashMap<String,String>>();
} //开始元素
//当遇到文档开头的时候会调用这个方法
@Override
public void startElement(String uri, String localName, String qname,Attributes attributes) throws SAXException {
// TODO Auto-generated method stub
//判断正在解析的元素是不是开始解析的元素
System.out.println("--startElement()--"+qname);
if(qname.equals(nodeName)){
map=new HashMap<String, String>();
}
if(attributes!=null&&map!=null){
for (int i = ; i < attributes.getLength(); i++) {
map.put(attributes.getQName(i), attributes.getValue(i));
}
}
System.out.println(qname+":"+map);
currentTag=qname;
} //元素内容
//用来处理xml文件所读取到的内容
@Override
public void characters(char[] ch, int start, int length) throws SAXException {
// TODO Auto-generated method stub
if(currentTag!=null&&map!=null){
currentVal=new String(ch,start,length);
if(currentVal!=null&&!currentVal.trim().equals("")&&!currentVal.trim().equals("\n")){
map.put(currentTag, currentVal);
}
}
System.out.println("--characters()--"+currentTag+" "+currentVal);
currentTag=null;//把当前节点对应标签和值设空
currentVal=null;
} //结束解析
//遇到结束标记的时候会调用这个方法
@Override
public void endElement(String uri, String localName, String qName)
throws SAXException {
// TODO Auto-generated method stub
System.out.println("--endElement()--"+qName);
if(qName.equals(nodeName)){
list.add(map);
map=null;
}
} //结束解析文档 //结束解析文档,即解析根元素结束标签时调用该方法
@Override
public void endDocument() throws SAXException {
// TODO Auto-generated method stub
System.out.println("--endDocument()--");
super.endDocument();
}
}
httpUtils.java
package com.sax.http; import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL; public class httpUtils {
public httpUtils (){ }
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();
connection.setDoInput(true);
connection.setRequestMethod("GET");
int code=connection.getResponseCode();
if(code==){
inputStream=connection.getInputStream();
} }
} catch (Exception e) {
// TODO: handle exception
}
return inputStream;
}
}
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 {
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;
} }
test.java
package com.sax.test; import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; import com.sax.http.httpUtils;
import com.sax.service.saxService; public class test { /**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path="http://122.206.79.193: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
}
} }
---------------------------------
XmlPull:
和Sax类似,是基于流(stream)操作文件,然后根据节点事件回调开发者编写的处理程序。
因为是基于流的处理,因此Xmlpull和 Sax都比较节约内存资源,不会象Dom那样要把所有节点以对橡树的形式展现在内存中。 但Xmlpull比Sax更简明,而且不需要扫描完整个流。

package com.xml.domain; public class person { private int id;
private String name;
private int age;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
@Override
public String toString() {
return "person [id=" + id + ", name=" + name + ", age=" + age + "]";
}
public person(int id, String name, int age) {
super();
this.id = id;
this.name = name;
this.age = age;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public person() {
// TODO Auto-generated constructor stub
} }
httpUtils
package com.xml.http; import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL; public class httpUtils {
public httpUtils (){ }
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();
connection.setDoInput(true);
connection.setRequestMethod("GET");
int code=connection.getResponseCode();
if(code==){
inputStream=connection.getInputStream();
} }
} catch (Exception e) {
// TODO: handle exception
}
return inputStream;
}
}
pullXmlTools
package com.xml.pull; import java.io.InputStream;
import java.util.ArrayList;
import java.util.List; import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import org.xmlpull.v1.XmlPullParserFactory; import com.xml.domain.person; /**
* 记得导入包
* @author Administrator
* 优点:比sax简单
* 缺点:swtich时需要知道节点名称
*
*/
public class pullXmlTools { public pullXmlTools() {
// TODO Auto-generated constructor stub
}
//inputStream:从服务器获取xml,以流的形式返回
public static List<person> parseXml(InputStream inputStream,String encode) throws Exception{
List<person> list=null;
person person=null;//装载解析的每个节点的内容
//创建xml工厂
XmlPullParserFactory factory=XmlPullParserFactory.newInstance();
//获得解析类
XmlPullParser parser= factory.newPullParser();
parser.setInput(inputStream, encode);
//获得事件的类型
int eventType=parser.getEventType();
while(eventType!=XmlPullParser.END_DOCUMENT){
switch (eventType) {
case XmlPullParser.START_DOCUMENT:
list=new ArrayList<person>();
break;
case XmlPullParser.START_TAG:
if("person".equals(parser.getName())){
person=new person();
int id=Integer.parseInt(parser.getAttributeValue());
person.setId(id);
}
else if("name".equals(parser.getName())){
String name=parser.nextText();//获取该节点的内容
person.setName(name);
}
else if("age".equals(parser.getName())){
int age=Integer.parseInt(parser.nextText());
person.setAge(age);
}
list=new ArrayList<person>();
break;
case XmlPullParser.END_TAG:
if("person".equals(parser.getName())){
list.add(person);
person=null;
}
break;
}
eventType=parser.next();//循环
}
return list; }
}
test
package com.xml.test; import java.io.InputStream;
import java.util.List; import com.xml.domain.person;
import com.xml.http.httpUtils;
import com.xml.pull.pullXmlTools; public class Test { public Test() {
// TODO Auto-generated constructor stub
} /**
* @param args
* @throws Exception
*/
public static void main(String[] args) throws Exception {
// TODO Auto-generated method stub
String path="http://122.206.79.193:8080/myhttp/person.xml";
InputStream inputStream=httpUtils.getXml(path);
List<person> list=pullXmlTools.parseXml(inputStream, "UTF-8");
for (person person : list) {
System.out.println(person.toString());
}
} }
-------------------------------
优点:a、由于整棵树在内存中,因此可以对xml文档随机访问
b、可以对xml文档进行修改操作
c、较sax,dom使用也更简单。
缺点:a、整个文档必须一次性解析完
b、由于整个文档都需要载入内存,对于大文档成本高


package com.xml.dom.domain; public class person { private int id;
private String name;
private int age;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
@Override
public String toString() {
return "person [id=" + id + ", name=" + name + ", age=" + age + "]";
}
public person(int id, String name, int age) {
super();
this.id = id;
this.name = name;
this.age = age;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public person() {
// TODO Auto-generated constructor stub
} }
http
package com.xml.dom.http; import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL; public class httpUtils {
public httpUtils (){ }
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();
connection.setDoInput(true);
connection.setRequestMethod("GET");
int code=connection.getResponseCode();
if(code==){
inputStream=connection.getInputStream();
} }
} catch (Exception e) {
// TODO: handle exception
}
return inputStream;
}
}
dom
package com.xml.dom.service; import java.io.InputStream;
import java.util.ArrayList;
import java.util.List; import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException; import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList; import com.xml.dom.domain.person; public class DomService { public DomService() {
// TODO Auto-generated constructor stub
} public List<person> getPersons(InputStream inputStream) throws Exception{
List<person> list=new ArrayList<person>();
DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();//创建dom解析工厂
DocumentBuilder builder=factory.newDocumentBuilder();//
Document dom=builder.parse(inputStream);//得到文档对象
Element element=dom.getDocumentElement();//获得稳定的元素节点
NodeList personNodes=element.getElementsByTagName("person");//从person节点开始遍历
for (int i = ; i < personNodes.getLength(); i++) {
Element personElement=(Element)personNodes.item(i);
person person=new person();
person.setId(Integer.parseInt(personElement.getAttribute("id")));
NodeList childNodes=personElement.getChildNodes();//该节点的所有属性
for (int j = ; j < childNodes.getLength(); j++) {
if(childNodes.item(j).getNodeType()==Node.ELEMENT_NODE){
if("name".equals(childNodes.item(j).getNodeName())){
person.setName(childNodes.item(j).getFirstChild().getNodeValue());
}
else if("age".equals(childNodes.item(j).getNodeName())){
person.setAge(Integer.parseInt(childNodes.item(j).getFirstChild().getNodeValue()));
}
}
}
list.add(person);
}
return list;
} }
test
package com.xml.dom.test; import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; import com.xml.dom.domain.person;
import com.xml.dom.http.httpUtils;
import com.xml.dom.service.DomService; public class test { /**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
String path="http://122.206.79.193:8080/myhttp/person.xml";
InputStream inputStream=httpUtils.getXml(path);
try {
DomService domService=new DomService();
List<person>list= domService.getPersons(inputStream);
for(person person:list){
System.out.println(person.toString());
}
} catch (Exception e) {
// TODO: handle exception
}
} }
三种方式的对比:
方式 | 是否提供服务器端jsonString的生成方法 | 优缺点 |
SAX |
首先创建自己的事件处理器类myHandler:myHandler extends DefaultHandler 其次,建立httpUtils,从服务器读取xml文件并返回读入流 第三,实例化工厂、解析对象和事件处理对象,通过使用解析器的解析方法对输入流进行解析,并通过时间处理器的get方法返回最终的结果 SAXParserFactory spf=SAXParserFactory.newInstance();//创建解析工厂对象 |
完美 |
PULL | 需要导入第三方的kxml2-2.2.2.jar
首先需要建立一个解析xml的方法,该方法有两个传入参数,InputStream inputStream,String encode 其次,建立httpUtils,从服务器读取xml文件并返回读入流 第三,完善第一步的方法:实例化工厂、解析对象,将输入流和编码方式设置给解析对象并通过解析器parser.getEventType()方法获得标签类型, while+switch方式遍历整个文档标签,获取相应的参数、对象并累加返回list person person=null;//装载解析的每个节点的内容//创建xml工厂 |
优点:简单 缺点:需要提前知道各个节点的名字 |
DOM |
首先需要建立一个解析xml的方法,该方法有两个传入参数,InputStream inputStream 其次,建立httpUtils,从服务器读取xml文件并返回读入流 第三,完善第一步的方法:实例化工厂、解析对象,将输入流设置给解析对象builder.parse(inputStream)获取文档对象, 然后通过文档对象的getDocumentElement方法获取稳定节点,然后遍历 DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();//创建dom解析工厂 |
缺点:有撑破内存的可能,极不推荐 |
---------------------------------
xml序列化:
public void xml(View view){
//初始化序列化器
XmlSerializer serializer= Xml.newSerializer();
File file=new File(Environment.getExternalStorageDirectory(),"xml.xml");
FileOutputStream os=new FileOutputStream(file);
serializer.setOutput(os, "utf-8"); serializer.startDocument("utf-8", true);//开头
serializer.startTag(null, "persons");
for(Person ps:PersonList){
serializer.startTag(null, "person");
serializer.attribute(null, "id", ps.getId()); serializer.startTag(null, "age");
serializer.text( ps.getname());
serializer.endTag(null, "age"); serializer.endTag(null, "person");
}
serializer.endTag(null, "persons");
serializer.endDocument();//结尾
}
Android 之xml解析的更多相关文章
- Android实现XML解析技术
转载:Android实现XML解析技术 本文介绍在Android平台中实现对XML的三种解析方式. XML在各种开发中都广泛应用,Android也不例外.作为承载数据的一个重要角色,如何读写XML成为 ...
- Android 简易XML解析
首先创建在Android工程中创建一个Assets文件夹 app/src/main/assets 在这里添加一个名为 data.xml的文件,然后编辑这个文件,加入如下XML格式内容 <?xml ...
- Android中XML解析
package com.example.thebroadproject; public class Book { private int id; private String name; privat ...
- Android项目--XML解析
对于xml文件,一般有两种解析方式: -----pull解析-------- -----Sax解析------- 如果xml文件是本地文件,那么就好说了 AssetManager assetManag ...
- Android,XML解析
XML解析三种方式 DOM 通用性强,它会将XML文件的所有内容读取到内存中,然后允许您使用DOM API遍历XML树.检索所需的数据: 简单直观,但需要将文档读取到内存,并不太适合移动设备: SAX ...
- Android中XML解析-Dom解析
Android中需要解析服务器端传过来的数据,由于XML是与平台无关的特性,被广泛运用于数据通信中,有的时候需要解析xml数据,格式有三种方式,分别是DOM.SAX以及PULL三种方式,本文就简单以D ...
- Android中XML解析-SAX解析
昨天由于时间比较匆忙只写了Android中的XML解析的Dom方式,这种方式比较方便,很容易理解,最大的不足就是内容多的时候,会消耗内存.SAX(Simple API for XML)是一个解析速度快 ...
- Android中XML解析-PULL解析
前面写了两篇XML解析的Dom和SAX方式,Dom比较符合思维方式,SAX事件驱动注重效率,除了这两种方式以外也可以使用Android内置的Pull解析器解析XML文件. Pull解析器的运行方式与 ...
- Android中XML解析,保存的三种方法
简单介绍 在Android开发中,关于XML解析有三种方式,各自是: SAX 基于事件的解析器.解析速度快.占用内存少.非常适合在Android移动设备中使用. DOM 在内存中以树形结构存放,因此检 ...
随机推荐
- 优化testng报告
背景 搞过testng的同学都知道,testng自带的报告非常丑,而且有些字段的展示很不人性化,所以需要优化下报告 解决方案 尝试过一下开源的jar包,如ReportNG,奈何和目前使用的allure ...
- awk 使用案例
1.输出占用率超过60%的分区 df -h | awk 'BEGIN{print "Full Partition"}NR>1{gsub("%"," ...
- 【可视化】Echarts3 在世界地图中绘制中国各省份的轮廓
要在世界地图展现出来的情况下绘制中国省份的轮廓,根据现有的echarts-api是不可行的. 但好在echarts也提供了自定义地图的方式,使用echarts.registerMap();来实现 第一 ...
- redis 介绍和常用命令
redis 介绍和常用命令 redis简介 Redis 是一款开源的,基于 BSD 许可的,高级键值 (key-value) 缓存 (cache) 和存储 (store) 系统.由于 Redis 的键 ...
- Ext:添加进度条
var myMask = new Ext.LoadMask(Ext.getBody(), {msg:"正在提交..."}); myMask.show(); myMask.hide( ...
- Entity Framework Core 2.0 中使用LIKE 操作符
Entity Framework Core 2.0 中使用LIKE 操作符 不定时更新翻译系列,此系列更新毫无时间规律,文笔菜翻译菜求各位看官老爷们轻喷,如觉得我翻译有问题请挪步原博客地址 本博文翻译 ...
- C#连接Firebird方法
Firebird Data Provider For .NET 连接 Firebird 数据库文件 下载 Firebird 嵌入式数据库:Firebird-2.5.0.25920-0_Win32_em ...
- 快速排序Java实现
package practice; import edu.princeton.cs.algs4.*; public class TestMain { public static void main(S ...
- spring mvc:@RequestParam与@ModelAttribute异同
关于spring mvc中的两个注解:@RequestParam.@ModelAttribute区别,原先并没有特别注意,直到最近找别人开发的一个小模块的bug时,才有意识的比较了两者的区别. 1.@ ...
- HTTP协议知多少-关于http1.x、http2、SPDY的相关知识
作为网站开发的基础协议,我们知道浏览器上都有输出http这四个字母,这意味着什么呢? 这就是最基础的HTTP协议. 逐浪君今天为各位大人准备了一些HTTP技术的知识,来和大家分享. 以下图为例: 这一 ...