在Android系统中解析XML文件的方法
前言
在学习android的framework层源码时,android大量的使用xmlpullparser来解析xml文件的源码。因此,这里也顺道介绍一下xmlpullparser的使用。
xml
xml(extensible markup language)中文名为可扩展标记语言。标记指计算机所能理解的信息符号,通过此种标记,计算机之间可以处理包含各种信息的文章等。
用途
xml设计用了传送及携带数据信息,不用了表现或展示数据,html语言则用了表现数据,所以xml用途的焦点是它说明数据是什么,以及携带数据信息。
- 丰富文件——自定文件描述并使其更丰富
- 元数据——描述其它文件或网络资讯
- 配置文档——描述软件设置的参数
结构
每个xml文档都由xml序言开始,在前面的代码中第一行就是xml序言,<?xml version="1.0"?>。这一行代码会告诉解析器或浏览器这个文件应该按照xml规则进行解析。但是,根元素的名称是由文档类型定义或xml纲要定义的。
xmlpullparser
pull解析xml是基于事件驱动的方式解析xml文件,pull开始解析时,我们可以先通过geteventtype()方法获取当前解析事件类型,并且通过next()方法获取下一个解析事件类型。pull解析器提供了start_document(开始文档)、end_document(结束文档)、start_tag(开始标签)、end_tag(结束标签)四种事件解析类型。当处于某个元素时,可以调用getattributevalue()方法获取属性的值,也可以通过nexttext()方法获取本节点的文本值。下面通过一个例子来进行解析。
xml示例文件
需要解析的xml示例文件代码如下:
<?xml version="1.0" encoding="utf-8"?> <colleagues> <colleague id="1"> <name>耗子</name> <age>24</age> <sex>boy</sex> </colleague> <colleague id="2"> <name>璐璐</name> <age>28</age> <sex>girl</sex> </colleague> <colleague id="3"> <name>陈善</name> <age>26</age> <sex>boy</sex> </colleague> </colleagues>
xmlpullparser解析器
package com.example.shakedemo; import java.io.file; import java.io.filenotfoundexception; import java.io.filereader; import java.io.ioexception; import java.util.arraylist; import java.util.list; import org.xmlpull.v1.xmlpullparser; import org.xmlpull.v1.xmlpullparserexception; import org.xmlpull.v1.xmlpullparserfactory; import android.r.xml; import android.util.log; import android.util.xml; public class xmlpullparserhelper { public static list<colleague> getcolleagues(string xmlfilepath) { list<colleague> colleagues = new arraylist<colleague>(); filereader xmlreader = null; try { xmlreader = new filereader(new file(xmlfilepath)); } catch (filenotfoundexception e) { log.e("wzy", "couldn't find xml file " + xmlfilepath); return colleagues; } try { // 方式1: 使用 android 提供的android.util.xml 类获取 parser 对象 xmlpullparser parser = xml.newpullparser(); // 方式2: 使用工厂类 xmlpullparserfactory // xmlpullparserfactory pullfactory = // xmlpullparserfactory.newinstance(); // xmlpullparser parser = pullfactory.newpullparser(); // 设置文件输入流 parser.setinput(xmlreader); // 得到当前事件类型 int eventtype = parser.geteventtype(); colleague colleague = null; while (eventtype != xmlpullparser.end_document) { switch (eventtype) { case xmlpullparser.start_document: break; case xmlpullparser.start_tag: /** * 通过getname判断读到哪个标签, 然后通过nexttext获取文本节点值, * 或者通过getattributevalue(i)获取属性节点值 */ string name = parser.getname(); if ("colleague".equals(name)) { colleague = new colleague(); colleague.setid(integer.parseint(parser.getattributevalue(null, "id"))); } else if ("name".equals(name)) { if (colleague != null) { colleague.setname(parser.nexttext()); } } else if ("age".equals(name)) { if (colleague != null) { colleague.setage(integer.parseint(parser.nexttext())); } } else if ("sex".equals(name)) { if (colleague != null) { colleague.setsex(parser.nexttext()); } } break; case xmlpullparser.end_tag: if ("colleague".equals(parser.getname()) && colleague != null) { colleagues.add(colleague); colleague = null; } break; } eventtype = parser.next(); } xmlreader.close(); } catch (xmlpullparserexception e) { // do nothing } catch (ioexception e) { // do nothing } return colleagues; } }
其中,colleague类的定义比较简单,代码如下:
package com.example.shakedemo; public class colleague { private int id; private int age; private string name; private string sex; public int getid() { return id; } public void setid(int id) { this.id = id; } public int getage() { return age; } public void setage(int age) { this.age = age; } public string getname() { return name; } public void setname(string name) { this.name = name; } public string getsex() { return sex; } public void setsex(string sex) { this.sex = sex; } @override public string tostring() { return "id is " + id + ", name is " + name + ", sex is " + sex; } }