加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

XML文件解析

发布时间:2020-12-16 00:14:48 所属栏目:百科 来源:网络整理
导读:一、xml文件的三种解析方式 1.DOM 在Dom解析的过程中,是先把dom全部文件读入到内存中,然后使用dom的api遍历所有数据,检索想要的数据,这种方式显然是一种比较消耗内存的方式,对于像手机这样的移动设备来讲,内存是非常有限的,所以对于比较大的XML文件,

一、xml文件的三种解析方式

1.DOM

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

2.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 qName)接收文档结束的标签

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

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

3.PULL

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

二、待解析的xml文件

<pre name="code" class="html"><?xml version="1.0" encoding="UTF-8"?>
<students>
   <student name="张三" age="20" sex="男">
       <introduction>张三是个乐观开朗的大男孩</introduction>
       <grade>大二</grade>
       <mclass>工业设计一班</mclass>
   </student>
   <student name="李四" age="23" sex="女">
       <introduction>李四爱唱歌</introduction>
       <grade>大四</grade>
       <mclass>计算机一班</mclass>
   </student>
   <student name="小米" age="23" sex="女">
       <introduction>小米爱吃大米</introduction>
       <grade>大四</grade>
       <mclass>美声一班</mclass>
   </student>
   <student name="森宿" age="22" sex="女">
       <introduction>森宿爱做衣服</introduction>
       <grade>大四</grade>
       <mclass>服装设计一班</mclass>
   </student>
</students>
 

三、将xml文件的数据抽象为实体类

package com.xmldemo.javabean;

import java.io.Serializable;

public class Student implements Serializable{

	private String name;
	private int age;
	private String sex;
	private String introduction;
	private String grade;
	private String mclass;
	
	
	public Student() {
		super();
	}


	public Student(String name,int age,String sex,String introduction,String grade,String mclass) {
		super();
		this.name = name;
		this.age = age;
		this.sex = sex;
		this.introduction = introduction;
		this.grade = grade;
		this.mclass = mclass;
	}


	public String getName() {
		return name;
	}


	public void setName(String name) {
		this.name = name;
	}


	public int getAge() {
		return age;
	}


	public void setAge(int age) {
		this.age = age;
	}


	public String getSex() {
		return sex;
	}


	public void setSex(String sex) {
		this.sex = sex;
	}


	public String getIntroduction() {
		return introduction;
	}


	public void setIntroduction(String introduction) {
		this.introduction = introduction;
	}


	public String getGrade() {
		return grade;
	}


	public void setGrade(String grade) {
		this.grade = grade;
	}


	public String getMclass() {
		return mclass;
	}


	public void setMclass(String mclass) {
		this.mclass = mclass;
	}
	
	
}


四、解析详解

1.DOM解析实例

public static List<Student> DomRead(String fileName) {
		List<Student> result=new ArrayList<Student>();
		File dir=new File(Environment.getExternalStorageDirectory()+"/dom");
		if(!dir.exists())
			dir.mkdirs();
		File file=new File(dir,fileName);
		//获取DOM工厂对象
		DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();
		try {
			//获取DocumentBuilder对象
			DocumentBuilder builder=factory.newDocumentBuilder();
			//获取文档对象
			Document document=builder.parse(file);
			//获取文档对象根目录
			Element root=document.getDocumentElement();
			//获取根目录下student节点
			NodeList nodeList=root.getElementsByTagName("student");
			for (int i = 0; i < nodeList.getLength(); i++) {
				Student student=new Student();
				//获取students下的子节点
				Element element=(Element) nodeList.item(i);
				//获取student里的属性值
				student.setName(element.getAttribute("name"));
				student.setAge(Integer.parseInt(element.getAttribute("age")));
				student.setSex(element.getAttribute("sex"));

				//获取student下的子节点introduction
				Element introduction=(Element) element.getElementsByTagName("introduction").item(0);
				//获取introduction节点的内容
				student.setIntroduction(introduction.getTextContent());

				//获取student下的子节点grade
				Element grade=(Element) element.getElementsByTagName("grade").item(0);
				//获取grade节点的内容
				student.setGrade(grade.getTextContent());

				//获取student下的子节点mclass
				Element mclass=(Element) element.getElementsByTagName("mclass").item(0);
				//获取mclass节点的内容
				student.setMclass(mclass.getTextContent());

				/*以下方法亦可
				//获取student下的子节点introduction
				Element introduction=(Element) element.getElementsByTagName("introduction").item(0);
				//获取introduction节点的内容
				student.setIntroduction(introduction.getFirstChild().getNodeValue());

				//获取student下的子节点grade
				Element grade=(Element) element.getElementsByTagName("grade").item(0);
				//获取grade节点的内容
				student.setGrade(grade.getFirstChild().getNodeValue());

				//获取student下的子节点mclass
				Element mclass=(Element) element.getElementsByTagName("mclass").item(0);
				//获取mclass节点的内容
				student.setMclass(mclass.getFirstChild().getNodeValue());*/

				result.add(student);
			}
		} catch (Exception e) {
		}
		return result;
	}





2.SAX解析实例

(1)实例化事件处理器,继承自DefaultHandler

package com.xmldemo.custom;

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 android.R.integer;

import com.xmldemo.javabean.Student;

public class StudentHandler extends DefaultHandler {

	//解析的student对象存储到list集合中
	private List<Student> students;
	//解析当前的student对象
	public Student student;
	//声明标签的名称
	public String tagName;
	//获取解析所有的student对象
	public List<Student> getStudents() {
		return students;
	}
	
	/**
	 * 文档开始触发的事件
	 */
	@Override
	public void startDocument() throws SAXException {
		super.startDocument();
		students=new ArrayList<Student>();
	}
	
	/**
	 * 读到元素标签是开始执行
	 */
	@Override
	public void startElement(String uri,Attributes attributes) throws SAXException {
		super.startElement(uri,localName,qName,attributes);
		//判断解析的标签是否是student,只有标签为student时才需要做读取属性操作,其他标签只需把标签名存进tagName
		//localName和qName的值一样
		if(localName.equals("student")){
			student=new Student();
			//读取student属性值
			student.setName(attributes.getValue("name"));
			student.setAge(Integer.parseInt(attributes.getValue("age")));
			student.setSex(attributes.getValue("sex"));
			//currentPerson.setId(Integer.parseInt(attributes.getValue(0)));
		}
		this.tagName=localName;
	}
	
	/**
	 * 读取文本内容时执行
	 */
	@Override
	public void characters(char[] ch,int length)
			throws SAXException {
		super.characters(ch,start,length);
		//首先判断tagName是否为空
		if(tagName!=null){
			String data=new String(ch,length);
			//判断标签是否为空
			if(tagName.equals("introduction")){//判断标签是否是introduction
				student.setIntroduction(data);
			}else if(tagName.equals("grade")){//判断标签是否是grade
				student.setGrade(data);
			}else if(tagName.equals("mclass")){//判断标签是否是mclass
				student.setMclass(data);
			}
		}
	}
	
	/**
	 * 元素标签结束时执行
	 */
	@Override
	public void endElement(String uri,String qName)
			throws SAXException {
		super.endElement(uri,qName);
		//当student标签结束的时候把students对象存储到集合中
		if(localName.equals("student")){
			students.add(student);
			student=null;
		}
		this.tagName=null;
	}
	
	/**
	 * 文档结束时执行
	 */
	@Override
	public void endDocument() throws SAXException {
		super.endDocument();
	}
	
}

(2)通过SAXParserFactory等获得事件源XMLReader,并连接到时间处理类DefaultHandler

<span style="font-size:18px;">public static List<Student> SaxRead(Context context,String fileName) {
		List<Student> result=new ArrayList<Student>();
		try {
			//获取输入流
			InputStream inputStream=context.getResources().getAssets().open(fileName);
			//获取sax解析器
			SAXParserFactory factory=SAXParserFactory.newInstance();
			SAXParser parser=factory.newSAXParser();
			StudentHandler studentHandler=new StudentHandler();
			//获取事件源
			XMLReader xmlReader=parser.getXMLReader();
			//为事件源设置内容处理器
			xmlReader.setContentHandler(studentHandler);
			xmlReader.parse(new InputSource(inputStream));
			result=studentHandler.getStudents();
			//以下方式也可解析
//			parser.parse(inputStream,studentHandler);
//			result=studentHandler.getStudents();
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return result;
	}</span>


3.PULL解析实例

public static List<Student> PullRead(Context context,String fileName) {
	List<Student> students=null;
	Student student=null;
	try {
		//获得文件输入流
		InputStream inputStream=context.getResources().getAssets().open(fileName);

		// 利用ANDROID提供的API快速获得pull解析器  
		XmlPullParser pullParser = Xml.newPullParser();  
		// 设置需要解析的XML数据,此时eventtype为 初始值START_DOCUMENT
		pullParser.setInput(inputStream,"UTF-8");  
		// 取得事件  
		int event = pullParser.getEventType();  
		// 若为解析到末尾  
		while (event != XmlPullParser.END_DOCUMENT) // 文档结束  
		{
			String nodeName = pullParser.getName();  
			switch (event)  
			{  
			case XmlPullParser.START_DOCUMENT: // 文档开始  
				students=new ArrayList<Student>();  
				break;  
			case XmlPullParser.START_TAG: // 标签开始  
				if ("student".equals(nodeName))  
				{  
					student = new Student(); 
					String name = pullParser.getAttributeValue(0);
					student.setName(name);
					String age = pullParser.getAttributeValue(1);
					student.setAge(Integer.parseInt(age));
					String sex = pullParser.getAttributeValue(2);
					student.setSex(sex);
				}  
				else if ("introduction".equals(nodeName))  
				{  
					/*If current event is START_TAG then if next element is 
						TEXT then element content is returned or if next event is 
						END_TAG then empty string is returned*/
					String introduction = pullParser.nextText();  
					student.setIntroduction(introduction);  
				}  
				else if ("grade".equals(nodeName))  
				{  
					String grade = pullParser.nextText();  
					student.setGrade(grade);  
				}  
				else if ("mclass".equals(nodeName))  
				{  
					String mclass = pullParser.nextText();  
					student.setMclass(mclass);
				} 
				break;  
			case XmlPullParser.END_TAG: // 标签结束  
				if ("student".equals(nodeName))  
				{  
					students.add(student);  
					student = null;  
				}  
				break;  
			default:
				break;
			} 
			event = pullParser.next(); // 下一个标签  
		} 
	} catch (Exception e) {
		// TODO Auto-generated catch block
		e.printStackTrace();
	}

	return students;
}

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读