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

XML文件解析之SAX解析

发布时间:2020-12-16 08:45:14 所属栏目:百科 来源:网络整理
导读:1.SAX概念 SXA:Simple API for XML 基于事件驱动(Android中的事件驱动基于回调函数),边加载边解析。 从头到尾逐个读取内容,修改不便,适用于只读的打文档。 用SAX解析XML文档的时候,在读取到文档开始和结束标签时候就会回调一个事件,在读到其他节点与
1.SAX概念
SXA:Simple API for XML
基于事件驱动(Android中的事件驱动基于回调函数),边加载边解析。
从头到尾逐个读取内容,修改不便,适用于只读的打文档。
用SAX解析XML文档的时候,在读取到文档开始和结束标签时候就会回调一个事件,在读到其他节点与内容的时候也会回调一个事件。
五个主要的回调方法:
startDocument() //处理文档解析开始事件
startElement() //处理元素开始事件
characters() //处理元素的字符内容,解析到元素的内容则返回到characters方法中
endElement() //处理元素结束事件
endDocument() //处理文档结束事件

2.基本步骤

(1)创建SAXParserFactory对象(newInstance())

(2)根据SAXParserFactory对象的newSAXParser()方法创建SAXParser解析器对象

(3)根据SAXParser解析器对象获得事件源对象XMLReader对象

(4)实例化一个DefaultHandler对象

(5)连接事件源对象到事件处理器DefaultHandler中(setContentHandler方法)

(6)使用XMLReader的parse方法解析从输入源中获取的XML数据

(7)通过DefaultHandler返回需要的数据集合


3.实例

需要解析的xml文档

<?xml version="1.0" encoding="utf-8"?>
	<students>
		<student id="0">
			<name>zhangmq</name>
			<gender>female</gender>
			<age>24</age>
		</student>
		<student id="1">
			<name>zhouhy</name>
			<gender>male</gender>
			<age>24</age>
		</student>
	</students>

根据xml文档定义的Student类

public class Student {

	private String id;
	private String name;
	private String gender;
	private String age;

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

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

	public String getGender() {
		return gender;
	}

	public void setGender(String gender) {
		this.gender = gender;
	}

	public String getAge() {
		return age;
	}

	public void setAge(String age) {
		this.age = age;
	}
	
	public String toString(){
		return "Student [id = "+id+" name = "+name +" gender = "+gender+" age = "+age+"]";
	}

}
具体解析代码
public class SAXParseHandler extends DefaultHandler {

	List<Student> students;

	Student student;

	String nodeName;   //记录当前的元素名字

	// 处理文档解析开始事件
	@Override
	public void startDocument() throws SAXException {
		// TODO Auto-generated method stub
		Log.d("zhangmq","startDocument");
		students = new ArrayList<Student>();
	}

	// 处理元素解析开始事件
	@Override
	public void startElement(String uri,String localName,String qName,Attributes attributes) throws SAXException {
		// TODO Auto-generated method stub
		Log.d("zhangmq","startElement");
		Log.d("zhangmq","startElement localName = " + localName);    
		Log.d("zhangmq","startElement qName = " + qName);         
		Log.d("zhangmq","startElement attributes.getLength() = "
						+ attributes.getLength());

		if (localName.equals("student")) {
			student = new Student();
			for (int i = 0; i < attributes.getLength(); i++) {
				if (attributes.getLocalName(i).equals("id")) {
					student.setId(attributes.getValue(i));
				}
			}
		} else {
			nodeName = localName;
		}
	}

	// 接收字符块通知
	@Override
	public void characters(char[] ch,int start,int length)
			throws SAXException {
		// TODO Auto-generated method stub
		Log.d("zhangmq","characters");
		Log.d("zhangmq","characters ch = " + ch);
		Log.d("zhangmq","characters start = " + start);
		Log.d("zhangmq","characters length = " + length);
		//这个地方比较容易失误
		//若是不加trim,则str可能是一个空字符串,但它不是普通的null或是"",而是"    ".
		//这样会导致判断str != null && !"".equals(str)的时候失误。千万要注意.
		//要判断str是因为还会解析</name>,得到的nodeName跟<name>是一样的.
		String str = String.valueOf(ch,start,length).trim();
		Log.d("zhangmq","characters str = " + str);
		Log.d("zhangmq","characters nodeName = " + nodeName);
		if (str != null && !"".equals(str)) {
			if ("name".equals(nodeName)) {
				student.setName(str);
			} else if ("gender".equals(nodeName)) {
				student.setGender(str);
			} else if ("age".equals(nodeName)) {
				student.setAge(str);
			}
		}
	}

	// 接收元素结束通知
	@Override
	public void endElement(String uri,String qName)
			throws SAXException {
		// TODO Auto-generated method stub
		Log.d("zhangmq","endElement");
		// 判断标签是否为student
		if (localName.equals("student")) {
			students.add(student);
		}
	}

	// 接收文档结束通知
	@Override
	public void endDocument() throws SAXException {
		// TODO Auto-generated method stub
		super.endDocument();
		Log.d("zhangmq","endDocument");
	}

	public String getStudentsString() {
		// 再需要+字符串时,str最好定义成"",否则,在显示字符串的时候最前面的是null,例如下面的就是:nullStudent
		String str = "";
		for (int i = 0; i < students.size(); i++) {
			str = str + students.get(i).toString() + "n";
		}
		return str;
	}

}
解析xml文档
public class SaxParseActivity extends Activity {

	private TextView sax_parse_tv;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		// TODO Auto-generated method stub
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_sax);

		sax_parse_tv = (TextView) findViewById(R.id.sax_parse);
		sax_parse_tv.setText(saxParseXml());
	}

	private String saxParseXml() {
		String str = null;
		SAXParserFactory factory = null;
		//解析器对象
		SAXParser parse = null;
		//事件源对象
		XMLReader reader = null;
		InputStream is = null;
		//SAX解析的帮助类,继承DefaultHandler
		SAXParseHandler parseHandler = null;
		
		//1.实例化SAXParserFactory对象
		factory = SAXParserFactory.newInstance();
		try {
			//2.使用SAXParserFactory对象实例化SAXParser对象
			parse = factory.newSAXParser();
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		try {
			//3.使用SAXParser对象实例化XMLReader
			reader = parse.getXMLReader();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		//自己写的SAX解析帮助类,实例化
		parseHandler = new SAXParseHandler();
		
		//解析器注册事件
		reader.setContentHandler(parseHandler);
		
		try {
			//获取xml文件到输入流中
			is = getResources().getAssets().open("dom_info.xml");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		InputSource inputSource = new InputSource(is);
		
		try {
			//解析文件,事件源
			reader.parse(inputSource);
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		str = parseHandler.getStudentsString();
		return str;
	}

}

(编辑:李大同)

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

    推荐文章
      热点阅读