一、DOM简单介绍
DOM
| 作用:把文档中的成员描述成一个个对象;
使用场景:使用Java代码操作XML、使用JavaScript操作HTML等等;
特点:在加载的时候,一次性把整个XML文档加载进内存,在内存中形成一棵树(Document对象),其实实际操作的是内存中的DOM树,和本地磁盘中的XML文件没有直接关系,要做同步操作把内存中的数据更新到XML文件(增删改操作完成之后,都需要做同步操作)。
缺点:若XML文件过大,可能造成内存溢出问题
注意:使用import导入类/接口,注意使用org.w3c组织的。 |
二、获取Document文档对象步骤:
操作步骤与顺序 | |
1、获取需要操作的XML文件的路径 | private File f = new File("xml文件路径"); |
2、创建DocumentBuilderFactory对象(工厂类中一般都有一个静态方法用于返回房前工厂类对象) | DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); |
3、根据工厂对象,创建DocumentBuilder对象 | DocumentBuilder builder = factory.newDocumentBuilder(); |
4、根据builder对象去解析一个已经存在的XML文件,从而得到Document对象 | Document doc = builder.parse(f); |
根据DocumentBuilder创建Document对象两种不同方式(newDocument和parse)比较:
Document doc = builder.newDocument(); | 当XML文档不存在的时候,使用此方式在内存中先创建出一颗树对象(Document) |
Document doc = builder.parse(File对象); | 当XML文档存在的时候,只需要直接解析即可 |
解析:一般指将String描述的事物转换为描述该事物的类型。
三、实际操作XML示例
XML文档内容:
<?xml version="1.0" encoding="UTF-8"?>
<contacts>
<linkman>
<name>xiaokeai</name>
<email>xxkk@qq.com</email>
<address>长沙</address>
<group>ttyy</group>
</linkman>
<linkman>
<name>xiaochihuo</name>
<email>xch@qq.com</email>
<address>成都</address>
<group>天河</group>
</linkman>
</contacts>
需求一:得到某个具体的文本节点内容 --> 取出第二个联系人
@Test
public void test1() throws Exception {
// 1、获取Document文档对象
Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(f);
// 2、获取XML中的根元素(contacts)
Element root = doc.getDocumentElement();
// 3、获取第二个联系人元素(linkman)
//获取根元素中所有linkman元素
Element linkmanE1 = (Element)root.getElementsByTagName("linkman").item(1);
// 4、获取linkman元素下的name子元素
Element nameE1 = (Element)linkmanE1.getElementsByTagName("name").item(0);
// 5、获取name元素的文本内容
Assert.assertEquals("xiaochihuo", nameE1.getTextContent()); //使用断言
}
Node中常用方法 |
| ||||||||
Document中常用方法 |
| ||||||||
Element中常用方法 |
|
需求二:修改第一个联系人的邮箱
@Test
public void test2() throws Exception {
// 1、获取Document文档对象
Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(f);
// 2、获取XML中的根元素(contacts)
Element root = doc.getDocumentElement();
// 3、获取第一个联系人元素(linkman)
Element linkmanE1 = (Element)root.getElementsByTagName("linkman").item(0);
// 4、获取linkman元素下的email子元素
Element emailE1 = (Element)linkmanE1.getElementsByTagName("email").item(0);
System.out.println(emailE1);
// 5、设置email元素的新的文本内容
emailE1.setTextContent("hello@qq.com");
// 6、同步操作:使用核心类Transformer
TransformerFactory factory = TransformerFactory.newInstance();
Transformer trans = factory.newTransformer();
Source xmlSource = new DOMSource(doc); //源:内存中的Document对象
Result outputTarget = new StreamResult(f); //目标:磁盘中的文件
trans.transform(xmlSource, outputTarget); //同步操作
}
需求三:增加一个新的联系人信息
@Test
public void test3() throws Exception{
// 1、获取Document文档对象
Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(f);
// 2、获取XML中的根元素(contacts)
Element root = doc.getDocumentElement();
// 3、创建一个linkman元素的片段
// 3.1创建linkman,name,email,address,group元素
Element linkmanEl = doc.createElement("linkman");
Element nameEl = doc.createElement("name");
Element emailEl = doc.createElement("email");
Element addressEl = doc.createElement("address");
Element groupEl = doc.createElement("group");
// 3.2给name,email,address,group元素设置文本内容
nameEl.setTextContent("haha");
emailEl.setTextContent("haha@qq.com");
addressEl.setTextContent("上海");
groupEl.setTextContent("無極限");
// 3.3把name,email,address,group元素作为linkman元素的子元素
linkmanEl.appendChild(nameEl);
linkmanEl.appendChild(emailEl);
linkmanEl.appendChild(addressEl);
linkmanEl.appendChild(groupEl);
// 3.4把linkman元素作为根元素的子元素
root.appendChild(linkmanEl);
// 4、同步操作
TransformerFactory factory = TransformerFactory.newInstance();
Transformer trans = factory.newTransformer();
Source xmlSource = new DOMSource(doc); //源:内存中的Document对象
Result outputTarget = new StreamResult(f); //目标:磁盘中的文件
trans.transform(xmlSource, outputTarget); //同步操作
}
需求四:给第三个联系人设置id属性,值为3,并获得其id属性
@Test
public void test4() throws Exception {
Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(f);
Element root = doc.getDocumentElement();
Element linkmanEl = (Element) root.getElementsByTagName("linkman").item(2);
// 设置id linkmanEl.setAttribute("id","3");
// 同步操作
TransformerFactory factory = TransformerFactory.newInstance();
Transformer trans = factory.newTransformer();
Source xmlSource = new DOMSource(doc);
// 源:内存中的Document对象
Result outputTarget = new StreamResult(f); //目标:磁盘中的文件
trans.transform(xmlSource, outputTarget); // 同步操作
// 获取id的值
String s = linkmanEl.getAttribute("id");
System.out.println(s);
}
需求五:删除第三个联系人的信息
@Test
public void test5() throws Exception {
Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(f);
Element root = doc.getDocumentElement();
Element linkmanEl = (Element) root.getElementsByTagName("linkman").item(2);
//删除
root.removeChild(linkmanEl);
// 同步操作
TransformerFactory factory = TransformerFactory.newInstance();
Transformer trans = factory.newTransformer();
Source xmlSource = new DOMSource(doc);
// 源:内存中的Document对象
Result outputTarget = new StreamResult(f); //目标:磁盘中的文件
trans.transform(xmlSource, outputTarget); // 同步操作
}
需求六:在内存中创建一个Document对象
DocumentBuilder builder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
Document doc = null;
// 如果XML文件存在就解析,否则就创建新文件
if (f.exists()) {
doc = builder.parse(f);
} else {
// 在内存中创建Document对象
doc = builder.newDocument();
// 创建根元素,并且把根元素作为文档的子元素
doc.appendChild(doc.createElement("contacts"));
}