粤嵌学习打卡第19天(基于DOM方式解析、生成XML文档)

今天我们来聊聊基于DOM方式实现解析和生成XML文档

一般web开发的xnl文档:


基于DOM处理XML文档

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SIQAETTW-1583586138269)(https://user-gold-cdn.xitu.io/2020/3/7/170b50697b3ab377?w=764&h=468&f=png&s=523521)]

1、DOM方式解析XML文档

<?xml version="1.0" encoding="UTF-8"?>
<accounts>
	<!-- 定义age属性 -->
	<account age="20" bankNo="10001">
		<id>610500199909022342</id>
		<name>张三</name>
		<money>5000.0</money>
	</account>
	<account age="21" bankNo="10002">
		<id>610500199709022342</id>
		<name>李四</name>
		<money>4500.0</money>
	</account>
</accounts>

实体类:

package com.yueqian.xml;
/**
 * 封装xml的实体类
 * @author LinChi
 *
 */
public class Account {
	private String bankNo;
	private int age;
	private String id;
	private String name;
	private double money;
	public Account() {
		super();
	}
	
	public Account(String bankNo, int age, String id, String name, double money) {
		super();
		this.bankNo = bankNo;
		this.age = age;
		this.id = id;
		this.name = name;
		this.money = money;
	}

	public int getAge() {
		return age;
	}
	public void setAge(int age) {
		this.age = 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 double getMoney() {
		return money;
	}
	public void setMoney(double money) {
		this.money = money;
	}
	
	public String getBankNo() {
		return bankNo;
	}
	public void setBankNo(String bankNo) {
		this.bankNo = bankNo;
	}
	@Override
	public String toString() {
		return this.bankNo+"|"+this.age+"|"+this.id+"|"+this.name+"|"+this.money;
	}
}

解析:

/**
	 * 解析xml文档
	 * @param filePath
	 * @return
	 * @throws ParserConfigurationException
	 * @throws SAXException
	 * @throws IOException
	 */
	public static List<Account> readXml(String filePath) throws ParserConfigurationException, SAXException, IOException{
		//过滤非法
		if(filePath == null || filePath.length()<=0) {
			System.out.println("ERROR: filePath args is null!");
			//返回null列表
			return Collections.EMPTY_LIST;
		}
		//创建文件
		File xmlFile = new File(filePath);
		//判断文件是否存在
		if(!xmlFile.exists()) {
			System.out.println("ERROR: filePath not exists!");
			//返回null列表
			return Collections.EMPTY_LIST;
		}
		//读取xml文件到列表
		List<Account> xmlList = new ArrayList<Account>();
		//获取DOM构建器的工厂对象
		DocumentBuilderFactory bf = DocumentBuilderFactory.newInstance();
		//通过工厂对象创建DOM构建器
		DocumentBuilder build = bf.newDocumentBuilder();
		//通过构建器对xml进行解析,获得Document对象节点
		Document doc = build.parse(xmlFile);
		//获得根节点
		Element rootEle = doc.getDocumentElement();
		//输出跟标签
//		System.out.println(rootEle.getTagName());
		//获取根标签下的所有子标签
		NodeList accNodeList = rootEle.getChildNodes();
		//遍历输出每个account标签
		for(int i = 0;i<accNodeList.getLength();i++) {
			//获取指定位置下的account节点
			Node node = accNodeList.item(i);
			//输出每个节点的名称
//			System.out.println(node.getNodeName());
			//跳过无用的文本信息构成的Node,即不是Element的节点
			if(!(node instanceof Element) ) {
				continue;
			}
			//将节点对象 Node转换为元素对象 Element
			Element accEle = (Element)node;
			//构造一个新的账户对象
			Account acc = new Account();
			//获取属性
			String ageAttr = null;
			String bankNo = null;
			//获得accEle上的所有属性
			NamedNodeMap accAttrs = accEle.getAttributes();
			//循环遍历所有属性值
			for(int j = 0;j<accAttrs.getLength();j++) {
				//循环遍历指定位置下的所有属性
				Node attrNode = accAttrs.item(j);
				//将attrNode 转换为 Attr属性
				Attr attr = (Attr)attrNode;
				//判断属性信息
				if("age".equals(attr.getNodeName())) {
					ageAttr = attr.getNodeValue();
				}
				if("bankNo".equals(attr.getNodeName())) {
					bankNo = attr.getNodeValue();
				}
			}
			System.out.println();
			int age = 0;
			//转换age为数值
			try {
				age = Integer.parseInt(ageAttr.trim());
			} catch (NumberFormatException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			//设置年龄属性
			acc.setAge(age);
			//设置银行账户属性
			acc.setBankNo(bankNo);
			//获取子标签 account标签的属性标签
			for(int k = 0;k<accEle.getChildNodes().getLength();k++) {
				Node subNode = accEle.getChildNodes().item(k);
				if(!(subNode instanceof Element) ) {
					continue;
				}
				//讲属性标签节点转换为Element
				Element accField = (Element)subNode;
				//判断是否为name标签
				if("name".equals(accField.getNodeName())) {
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setName(accField.getTextContent());
				}
				//判断是否为id标签
				if("id".equals(accField.getNodeName())) {
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setId(accField.getTextContent());
				}
				//判断是否为name标签
				if("money".equals(accField.getNodeName())) {
					double money = 0;
					try {
						money = Double.parseDouble(accField.getTextContent());
					} catch (NumberFormatException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					} catch (DOMException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setMoney(money);
				}
			}
			//添加对象到列表
			xmlList.add(acc);
		}
		return xmlList;
	}

测试:

public static void main(String[] args) {
		try {
			List<Account> list = readXml("xml/Test.xml");
			System.out.println(list);
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

成果截图:

2、DOM方式生成XML文档

生成:

/**
	 * 生成xml文档
	 * @param path  文件路径
	 * @param fileName  文件名称
	 * @param data  集合列表
	 * @return
	 * @throws ParserConfigurationException 
	 * @throws TransformerException 
	 */
	public static boolean writeXml(String path,String fileName,List<Account> data) throws ParserConfigurationException, TransformerException{
		//非法操作
		if(path == null || path.length()<=0 ||
				fileName == null || fileName.length()<=0 ||
						data == null || data.size()<=0) {
			System.out.println("ERROR: filePath args is null!");
			//返回null列表
			return false;
		}
		File dir = new File(path);
		//判断文件是否存在,不存在则创建
		if(!dir.exists()) {
			dir.mkdirs();
		}
		//检测文件是否存在
		File xmlFile = new File(dir, fileName);
		//获取DOM工厂对象
		DocumentBuilderFactory bf = DocumentBuilderFactory.newInstance();
		//根据工厂对象创建构建者
		DocumentBuilder build = bf.newDocumentBuilder();
		//根据构建者创建DOM文档树
		Document doc = build.newDocument();
		//建立根节点
		Element rootEle = doc.createElement("accounts");
		//将根节点添加到文档树中
		doc.appendChild(rootEle);
		//循环Account对象列表,构造account的xml表示
		for(Account acc:data) {
			//构造account节点
			Element accEle = doc.createElement("account");
			//为account节点设置其属性
			accEle.setAttribute("age", String.valueOf(acc.getAge()));
			accEle.setAttribute("bankNo", acc.getBankNo());
			//添加account节点到accounts上
			rootEle.appendChild(accEle);
			//添加id子标签
			Element idEle = createSubElement(doc,"id",acc.getId());
			//添加id节点到account节点
			accEle.appendChild(idEle);
			//添加name子标签
			Element nameEle = createSubElement(doc,"name",acc.getName());
			//添加id节点到account节点
			accEle.appendChild(nameEle);
			//添加money子标签
			Element moneyEle = createSubElement(doc,"money",String.valueOf(acc.getMoney()));
			//添加id节点到account节点
			accEle.appendChild(moneyEle);
		}
		//将添加的树状结构写入到doc
		TransformerFactory factory = TransformerFactory.newInstance();
		Transformer tf = factory.newTransformer();
		DOMSource source = new DOMSource(doc);
		StreamResult result = new StreamResult(xmlFile);
		tf.transform(source, result);
		return true;
	}
	/**
	 * 建立一个含有简单文本内容的Element对象
	 * @param doc
	 * @param tagName
	 * @param textContext
	 * @return
	 */
	
	private static Element createSubElement(Document doc,String tagName,String textContext) {
		//创建Element对象
		Element element = doc.createElement(tagName);
		//添加文本内容,文本内容需要添加到TextNode节点
		Text text = doc.createTextNode(textContext);
		//添加文本内容到标签
		element.appendChild(text);
		return element;
	}

测试:

//写xml文件
public static void main(String[] args) {
		List<Account> accList = new ArrayList<Account>();
		accList.add(new Account("acc1003", 25, "610105200210102233" ,"小王", 6000.0));
		
		try {
			System.out.println(writeXml("I:/","accs.xml",accList));
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (TransformerException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

成果截图:

true

3、DOM读写XML源码

package com.yueqian.xml;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;

import org.w3c.dom.Attr;
import org.w3c.dom.DOMException;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.w3c.dom.Text;
import org.xml.sax.SAXException;
import org.xml.sax.XMLFilter;

/**
 * DOM方式读写xml文件工具类
 * @author LinChi
 *
 */
public class TestXml {
	public static void main(String[] args) {
		try {
			List<Account> list = readXml("xml/Test.xml");
			System.out.println(list);
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		//写xml文件
		List<Account> accList = new ArrayList<Account>();
		accList.add(new Account("acc1003", 25, "610105200210102233" ,"小王", 6000.0));
		
		try {
			System.out.println(writeXml("I:/","accs.xml",accList));
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (TransformerException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	/**
	 * 解析xml文档
	 * @param filePath
	 * @return
	 * @throws ParserConfigurationException
	 * @throws SAXException
	 * @throws IOException
	 */
	public static List<Account> readXml(String filePath) throws ParserConfigurationException, SAXException, IOException{
		//过滤非法
		if(filePath == null || filePath.length()<=0) {
			System.out.println("ERROR: filePath args is null!");
			//返回null列表
			return Collections.EMPTY_LIST;
		}
		//创建文件
		File xmlFile = new File(filePath);
		//判断文件是否存在
		if(!xmlFile.exists()) {
			System.out.println("ERROR: filePath not exists!");
			//返回null列表
			return Collections.EMPTY_LIST;
		}
		//读取xml文件到列表
		List<Account> xmlList = new ArrayList<Account>();
		//获取DOM构建器的工厂对象
		DocumentBuilderFactory bf = DocumentBuilderFactory.newInstance();
		//通过工厂对象创建DOM构建器
		DocumentBuilder build = bf.newDocumentBuilder();
		//通过构建器对xml进行解析,获得Document对象节点
		Document doc = build.parse(xmlFile);
		//获得根节点
		Element rootEle = doc.getDocumentElement();
		//输出跟标签
//		System.out.println(rootEle.getTagName());
		//获取根标签下的所有子标签
		NodeList accNodeList = rootEle.getChildNodes();
		//遍历输出每个account标签
		for(int i = 0;i<accNodeList.getLength();i++) {
			//获取指定位置下的account节点
			Node node = accNodeList.item(i);
			//输出每个节点的名称
//			System.out.println(node.getNodeName());
			//跳过无用的文本信息构成的Node,即不是Element的节点
			if(!(node instanceof Element) ) {
				continue;
			}
			//将节点对象 Node转换为元素对象 Element
			Element accEle = (Element)node;
			//构造一个新的账户对象
			Account acc = new Account();
			//获取属性
			String ageAttr = null;
			String bankNo = null;
			//获得accEle上的所有属性
			NamedNodeMap accAttrs = accEle.getAttributes();
			//循环遍历所有属性值
			for(int j = 0;j<accAttrs.getLength();j++) {
				//循环遍历指定位置下的所有属性
				Node attrNode = accAttrs.item(j);
				//将attrNode 转换为 Attr属性
				Attr attr = (Attr)attrNode;
				//判断属性信息
				if("age".equals(attr.getNodeName())) {
					ageAttr = attr.getNodeValue();
				}
				if("bankNo".equals(attr.getNodeName())) {
					bankNo = attr.getNodeValue();
				}
			}
			System.out.println();
			int age = 0;
			//转换age为数值
			try {
				age = Integer.parseInt(ageAttr.trim());
			} catch (NumberFormatException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			//设置年龄属性
			acc.setAge(age);
			//设置银行账户属性
			acc.setBankNo(bankNo);
			//获取子标签 account标签的属性标签
			for(int k = 0;k<accEle.getChildNodes().getLength();k++) {
				Node subNode = accEle.getChildNodes().item(k);
				if(!(subNode instanceof Element) ) {
					continue;
				}
				//讲属性标签节点转换为Element
				Element accField = (Element)subNode;
				//判断是否为name标签
				if("name".equals(accField.getNodeName())) {
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setName(accField.getTextContent());
				}
				//判断是否为id标签
				if("id".equals(accField.getNodeName())) {
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setId(accField.getTextContent());
				}
				//判断是否为name标签
				if("money".equals(accField.getNodeName())) {
					double money = 0;
					try {
						money = Double.parseDouble(accField.getTextContent());
					} catch (NumberFormatException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					} catch (DOMException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
					//设置姓名属性 标签元素之间的元素用Element对象.getTextContent()
					acc.setMoney(money);
				}
			}
			//添加对象到列表
			xmlList.add(acc);
		}
		return xmlList;
	}
	
	/**
	 * 生成xml文档
	 * @param path  文件路径
	 * @param fileName  文件名称
	 * @param data  集合列表
	 * @return
	 * @throws ParserConfigurationException 
	 * @throws TransformerException 
	 */
	public static boolean writeXml(String path,String fileName,List<Account> data) throws ParserConfigurationException, TransformerException{
		//非法操作
		if(path == null || path.length()<=0 ||
				fileName == null || fileName.length()<=0 ||
						data == null || data.size()<=0) {
			System.out.println("ERROR: filePath args is null!");
			//返回null列表
			return false;
		}
		File dir = new File(path);
		//判断文件是否存在,不存在则创建
		if(!dir.exists()) {
			dir.mkdirs();
		}
		//检测文件是否存在
		File xmlFile = new File(dir, fileName);
		//获取DOM工厂对象
		DocumentBuilderFactory bf = DocumentBuilderFactory.newInstance();
		//根据工厂对象创建构建者
		DocumentBuilder build = bf.newDocumentBuilder();
		//根据构建者创建DOM文档树
		Document doc = build.newDocument();
		//建立根节点
		Element rootEle = doc.createElement("accounts");
		//将根节点添加到文档树中
		doc.appendChild(rootEle);
		//循环Account对象列表,构造account的xml表示
		for(Account acc:data) {
			//构造account节点
			Element accEle = doc.createElement("account");
			//为account节点设置其属性
			accEle.setAttribute("age", String.valueOf(acc.getAge()));
			accEle.setAttribute("bankNo", acc.getBankNo());
			//添加account节点到accounts上
			rootEle.appendChild(accEle);
			//添加id子标签
			Element idEle = createSubElement(doc,"id",acc.getId());
			//添加id节点到account节点
			accEle.appendChild(idEle);
			//添加name子标签
			Element nameEle = createSubElement(doc,"name",acc.getName());
			//添加id节点到account节点
			accEle.appendChild(nameEle);
			//添加money子标签
			Element moneyEle = createSubElement(doc,"money",String.valueOf(acc.getMoney()));
			//添加id节点到account节点
			accEle.appendChild(moneyEle);
		}
		//将添加的树状结构写入到doc
		TransformerFactory factory = TransformerFactory.newInstance();
		Transformer tf = factory.newTransformer();
		DOMSource source = new DOMSource(doc);
		StreamResult result = new StreamResult(xmlFile);
		tf.transform(source, result);
		return true;
	}
	/**
	 * 建立一个含有简单文本内容的Element对象
	 * @param doc
	 * @param tagName
	 * @param textContext
	 * @return
	 */
	
	private static Element createSubElement(Document doc,String tagName,String textContext) {
		//创建Element对象
		Element element = doc.createElement(tagName);
		//添加文本内容,文本内容需要添加到TextNode节点
		Text text = doc.createTextNode(textContext);
		//添加文本内容到标签
		element.appendChild(text);
		return element;
	}
	
}

今天的内容就分享到这了!期待明天的SAX方式解析XML文档

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值