概述

​ SAX,全称Simple API for XML,是一种以事件驱动的XMl API,是XML解析的一种新的替代方法,解析XML常用的还有DOM解析,PULL解析(Android特有),SAX与DOM不同的是它边扫描边解析,自顶向下依次解析,由于边扫描边解析,所以它解析XML具有速度快,占用内存少的优点,对于Android等CPU资源宝贵的移动平台来说是一个巨大的优势。

SAX的优点

  1. 解析速度快
  2. 占用内存少

SAX的缺点

  1. 解析过程中,只知道当前解析的标签的名字和属性
  2. 只能解析,不能修改xml文件
  3. 无法随机访问某个标签(自上而下一一解析)

SAX解析适用场合

  1. 对于CPU资源宝贵的设备,如Android等移动设备
  2. 对于只需要解析而无需修改的需求

步骤

  1. 获取xml文件输入流
  2. 获取SAX解析对象工厂
  3. 获取SAX解析对象
  4. 获取转化规则Handler
  5. 加载文件流和转化规则
  6. 解析

代码实现

xml文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?xml version="1.0" encoding="UTF-8"?>
<students>
<student id="1">
<name>张三1</name>
<age>1</age>
</student>
<student id="2">
<name>张三2</name>
<age>2</age>
</student>
<student id="3">
<name>张三3</name>
<age>3</age>
</student>
<student id="4">
<name>张三4</name>
<age>4</age>
</student>
<student id="5">
<name>张三5</name>
<age>5</age>
</student>
</students>

实体类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
public class Student {
private int studentId;
private String studentName;
private int studentAge;

public int getStudentId() {
return studentId;
}

public void setStudentId(int studentId) {
this.studentId = studentId;
}

public String getStudentName() {
return studentName;
}

public void setStudentName(String studentName) {
this.studentName = studentName;
}

public int getStudentAge() {
return studentAge;
}

public void setStudentAge(int studentAge) {
this.studentAge = studentAge;
}

@Override
public String toString() {
return "Student [studentAge=" + studentAge + ", studentId=" + studentId
+ ", studentName=" + studentName + "]";
}

public Student() {
super();
// TODO Auto-generated constructor stub
}

public Student(int studentId, String studentName, int studentAge) {
super();
this.studentId = studentId;
this.studentName = studentName;
this.studentAge = studentAge;
}

}

解析规则Handler类

  • startDocument():开始读取文档时调用
  • startElement():读取开始标签时调用
  • characters():读取文本时调用
  • endElement():读取结束标签时调用
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
public class StudentHandle extends DefaultHandler {

private List<Student> stuList;
private Student student = null;
private String temp;

public List<Student> getStuList() {
return stuList;
}

@Override
public void characters(char[] ch, int start, int length)
throws SAXException {
if ("name".equals(temp)) {
String studentName = new String(ch, start, length);
student.setStudentName(studentName);
} else if ("age".equals(temp)) {
String studentAge = new String(ch, start, length);
student.setStudentAge(Integer.parseInt(studentAge));
}
}

@Override
public void endElement(String uri, String localName, String qName)
throws SAXException {
if ("student".equals(qName)) {
stuList.add(student);
student = null;
}
temp = null;
}

@Override
public void startDocument() throws SAXException {
stuList = new ArrayList<Student>();
}

@Override
public void startElement(String uri, String localName, String qName,
Attributes attributes) throws SAXException {
if ("student".equals(qName)) {
if (null == student) {
student = new Student();
}
String studentId = attributes.getValue("", "id");
student.setStudentId(Integer.parseInt(studentId));
} else if ("name".equals(qName)) {
temp = "name";
} else if ("age".equals(qName)) {
temp = "age";
}
}

}

业务类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
public static List<Student> ReadXml() throws Exception {

//获取xml文件输入流
InputStream is = Thread.currentThread().getContextClassLoader().getResourceAsStream("student.xml");
//获取sax解析工厂
SAXParserFactory factory = SAXParserFactory.newInstance();
//获取sax解析类
SAXParser saxParser = factory.newSAXParser();
//获取转化规则
StudentHandle studentHandle = new StudentHandle();
//加载文件流和转化规则
saxParser.parse(is, studentHandle);
//转化
List<Student> stuList = studentHandle.getStuList();
//返回
return stuList;

}