认识 XML
XML 是 Extensible Markup Language 的简称,即可扩展标记语言的缩写;XML是一种简单的数据存储语言,使用一系列简单的标记来描述数据
XML特点
- XML与操作系统、编程语言的开发平台都无关
- 规范统一
- 实现不同系统之间的数据交换
XML作用
- 常用于数据交互
- 配置应用程序和网站
- 作为 Ajax 基石
XML文档格式
<?xml version="1.0" encoding="utf-8" ?>
<!--注释内容-->
<books>
<book id="1" name="金瓶梅" author="兰陵笑笑生">
<description>古典文学著作,阅读量很高</description>
</book>
<book id="2" name="三国志" author="陈寿">
<description>陈寿拍司马懿马屁的著作</description>
</book>
<book id="3" name="红楼" author="曹雪芹"/>
</books>
1、XML声明
一个 XML 文档必须在第一行对其进行声明,表示该文件是一个 XML 文档,如上第一行代码表示 XML 的声明,它定义了 XML 的版本和使用的编码格式等信息
- version:文档符合 XML1.0 规范
- encoding:文档字符编码
2、标签
在 XML 中,用尖括号<>括起来的各种标签来标记数据,标签需要成对使用来界定字符数据,例如< book>< /book>这对标签中,前面是开始标签,后面是结束标签,中间是标签描述的内容,XML可以包含任意数量的标签
<元素名 属性名=“属性值”>元素内容</元素名>
3、根元素
每个 XML 文档必须有且仅有一个根元素,例如< books>< /books>
- 根元素是一个完全包括文档中其他所有元素的元素
- 根元素的起始标签要放在所有其他元素的起始标签之前
- 根元素的结束标签要放在所有其他元素的结束标签之后
4、元素
XML 文档的主要部分的元素,元素由开始标签、元素内容和结束标签组成,元素内容可以包含子元素、字符数据等
5、属性
指元素名后面定义的数据,叫元素属性,多个属性之间用空格分隔;元素属性也可以用子标签的形式写在标签内,属性语法定义格式如下
<元素名 属性名1="属性值1" 属性名2="属性值2">
6、XML 中的特殊字符的处理
在 XML 文档中,有时在元素的文本中会出现一些特殊字符,而 XML 文档结构本身就用到了这些特殊字符,所以不能正确解析包含特殊字符的内容
(1)对字符转义,即使用 XML 中的预定义实体代替这些字符,预定义实体和特殊字符的对应关系图如下
实体名称 | 字符 |
---|---|
< | < |
> | > |
& | & |
" | " |
&apos | ’ |
(2)如果在元素的文本中有大量的特殊字符,可以使用 CDATA 节处理
CDATA 节中的所有字符都会被当作元素字符数据的常量部分,而不是 XML 标签,定义 CDATA 节的语法格式如下
<![CDATA[
要显示的字符
]]>
7、XML 中的注释
XML文档中注释的语法格式如下
<!--注释内容-->
XML编写注意事项
- 所有XML元素都必须有结束标签
- XML标签区分大小写
- XML必须正确的嵌套
- 同级标签以缩进对齐
- 元素名称可以包含字母、数字或其他的字符
- 元素名称不能以数字或者标点符号开始
- 元素名称中不能含空格
读取 XML 文档
储存手机信息的 XML 文档
<?xml version="1.0" encoding="GB2312"?>
<PhoneInfo>
<brand name="华为">
<type>
P30
</type>
<type>
mate30
</type>
<type>
P40pro
</type>
<type name="P30"/>
<type name="mate30"/>
<type name="P40pro"/>
</brand>
<brand name="苹果">
<type>iPhone11</type>
<type>iPhoneX</type>
<type name="iPhone11"/>
<type name="iPhoneX"/>
</brand>
</PhoneInfo>
读取该 XML 文档内容
public class TestXML {
Document document;
public void setDocument(String xmlParth){
DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();
try {
DocumentBuilder builder=factory.newDocumentBuilder();
document=builder.parse(xmlParth);
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) throws Exception {
TestXML xml=new TestXML();
xml.setDocument("phone_info.xml");
Document document;
DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();
DocumentBuilder builder=factory.newDocumentBuilder();
document=builder.parse("phone_info.xml");
NodeList brands = document.getElementsByTagName("brand");
Node item=brands.item(0);
Element e=(Element)item;
System.out.println(e.getAttribute("name"));
NodeList hwTypes=e.getChildNodes();
//遍历输出
for (int i = 0; i < hwTypes.getLength(); i++) {
Node n=hwTypes.item(i);
if (n instanceof Element){
Element type=(Element)n;
Node firstChild=type.getFirstChild();
if (firstChild instanceof Text){
Text t1=(Text)firstChild;
System.out.println(t1.getWholeText().trim());
}
}
}
System.out.println();
Node item1=brands.item(1);
Element e1=(Element)item1;
System.out.println(e1.getAttribute("name"));
NodeList hwTypes1=e1.getChildNodes();
for (int i = 0; i < hwTypes1.getLength(); i++) {
Node n1=hwTypes1.item(i);
if (n1 instanceof Element){
Element type1=(Element)n1;
Node firstChild=type1.getFirstChild();
if (firstChild instanceof Text){
Text t1=(Text)firstChild;
System.out.println(t1.getWholeText().trim());
}
}
}
}
}
写入 XML 文档
写入前的 XML 文档
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<PhoneInfo>
<brand name="华为">
<type>P30</type>
<type>mate30</type>
<type>P40pro</type>
</brand>
<brand name="苹果">
<type>iPhone11</type>
<type>iPhoneX</type>
</brand>
</PhoneInfo>
将内容写入到 XML 中,例如将三星手机信息写入到该 XML 文档中
保存XML文件步骤
- 获得TransformerFactory对象
- 创建Transformer对象
- 创建DOMSource对象
– 包含XML信息 - 设置输出属性
– 编码格式 - 创建StreamResult对象
– 包含保存文件的信息 - 将XML保存到指定文件中
public class TestXML {
Document document;
public void setDocument(String xmlParth){
DocumentBuilderFactory factory=DocumentBuilderFactory.newInstance();
try {
DocumentBuilder builder=factory.newDocumentBuilder();
document=builder.parse(xmlParth);
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) throws Exception {
TestXML xml=new TestXML();
xml.setDocument("phone_info.xml");
NodeList brands = xml.document.getElementsByTagName("brand");
Node item=brands.item(0);
Element e=(Element)item;
System.out.println(e.getAttribute("name"));
NodeList hwTypes=e.getChildNodes();
//创建节点并追加到根节点
Node root = xml.document.getElementsByTagName("PhoneInfo").item(0);
Element sx=xml.document.createElement("brand");
sx.setAttribute("name","三星");
Element sxType=xml.document.createElement("type");
sxType.setAttribute("name","note20");
sx.appendChild(sxType);
root.appendChild(sx);
//保存更改
TransformerFactory tf=TransformerFactory.newInstance();
tf.setAttribute("indent-number",new Integer(4));
Transformer t=tf.newTransformer();
t.setOutputProperty(OutputKeys.INDENT,"yes");//标注换行
t.setOutputProperty(OutputKeys.ENCODING,"UTF-8");//标注字节编码
DOMSource source=new DOMSource(xml.document);
FileOutputStream fos=new FileOutputStream("phone_info.xml");
StreamResult sr=new StreamResult(new OutputStreamWriter(fos) {
});
t.transform(source,sr);
}
}
运行后 XML 文档内容为
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<PhoneInfo>
<brand name="华为">
<type>P30</type>
<type>mate30</type>
<type>P40pro</type>
</brand>
<brand name="苹果">
<type>iPhone11</type>
<type>iPhoneX</type>
</brand>
<brand name="三星">
<type name="note20"/>
</brand>
</PhoneInfo>