问:SAX方式怎样解析XML文件?
Java Sax解析是按照xml文件的顺序一步一步的来解析
(1)示例代码:
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Result;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.sax.SAXTransformerFactory;
import javax.xml.transform.sax.TransformerHandler;
import javax.xml.transform.stream.StreamResult;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.AttributesImpl;
import org.xml.sax.helpers.DefaultHandler;
public class SaxResolve extends DefaultHandler {
public static void main(String[] args) throws IOException{
String file = "file/books.xml";
InputStream inputStream = new FileInputStream(file);
SaxResolve saxResove = new SaxResolve();
//1.解析xml文件
try {
List<Book> bookList = saxResove.getBooks(inputStream);
for(Book book : bookList ){
System.out.println(book.toString());
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
//2.创建xml文件
saxResove.saxCreateXML();
}
/**
* SAX方式解析xml文件
*
*/
private List<Book> books =null;
private Book book = null;
private String preTag = null;//记录解析时上一个节点名称
public List<Book> getBooks(InputStream inputStream) throws Exception{
SAXParserFactory spf = SAXParserFactory.newInstance();
SAXParser sp = spf.newSAXParser();
SaxResolve handler = new SaxResolve();
sp.parse(inputStream, handler);
return handler.getBooks();
}
public List<Book>getBooks(){
return books;
}
//开始解析
@Override
public void startDocument() throws SAXException {
books = new ArrayList<Book>();
}
//开始遍历xml标签
@Override
public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
if("book".equals(qName)){
book = new Book();
book.setId(Integer.parseInt(attributes.getValue(0)));
}
preTag = qName;//将正在解析的节点名称赋给preTag
}
//结束遍历xml标签
@Override
public void endElement(String uri, String localName, String qName) throws SAXException {
if("book".equals(qName)){
books.add(book);
book=null;
}
preTag = null;//解析结束时置为空
}
@Override
public void characters(char[] ch, int start, int length) throws SAXException {
if(preTag!=null){
String content = new String(ch,start,length);
if("bookName".equals(preTag)){
book.setBookName(content);
}else if("author".equals(preTag)){
book.setAuthor(content);
}else if("year".equals(preTag)){
book.setYear(content);
}
}
}
/**
* SAX方式创建xml文件
*/
public void saxCreateXML(){
//创建SAXTransformerFactory实例
SAXTransformerFactory sff = (SAXTransformerFactory) SAXTransformerFactory.newInstance();
//创建TransformerHandler实例
try {
TransformerHandler handler = sff.newTransformerHandler();
//创建transformer实例
Transformer tf = handler.getTransformer();
//设置输出属性
tf.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
tf.setOutputProperty(OutputKeys.INDENT,"yes");
//创建result对象,将此对象加载到transHandler中
// 1、这一步必须在Transformer.setOutputProperty()之后,不然设置的xml属性将不生效
// 2、这一步也必须在TransformerHandler.startDocument()之前,不然会报错。
// 分析源码后发现,startDocument()会先判断result是否为空,为空则报错
Result result = new StreamResult("file/csax.xml");
handler.setResult(result);
//创建属性attribute对象
AttributesImpl attr = new AttributesImpl();
//开始写文件
handler.startDocument();
//写入根节点
handler.startElement("", "", "bookstore", attr);
//清空属性,每次新增节点后都需要清空下属性
attr.clear();
//设置属性
attr.addAttribute("", "", "id", "", "1");
//写入根节点的子节点
handler.startElement("", "", "book", attr);
attr.clear();
//写入book子节点
handler.startElement("", "", "name", attr);
handler.characters("冰与火之歌".toCharArray(), 0, "冰与火之歌".toCharArray().length);
//写入子节点末尾
handler.endElement("", "", "name");
handler.startElement("", "", "year", attr);
handler.characters("2004".toCharArray(), 0, "2004".toCharArray().length);
handler.endElement("", "", "year");
handler.startElement("", "", "price", attr);
handler.characters("89".toCharArray(), 0, "89".toCharArray().length);
handler.endElement("", "", "price");
attr.clear();
//写入book节点末尾
handler.endElement("", "", "book");
//写入根节点末尾
handler.endElement("", "", "bookstore");
//写文件结束
handler.endDocument();
} catch (TransformerConfigurationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SAXException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
(2)Book实体类代码:
public class Book {
private int id; //id-book
private String bookName; //书名
private String author; // 作者
private String year;//年份
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getBookName() {
return bookName;
}
public void setBookName(String bookName) {
this.bookName = bookName;
}
public String getAuthor() {
return author;
}
public void setAuthor(String author) {
this.author = author;
}
public String getYear() {
return year;
}
public void setYear(String year) {
this.year = year;
}
@Override
public String toString() {
return this.id+"---"+this.bookName+"---"+this.author+"---"+this.year;
}
}
(3)创建的csax.xml文件截图如下: