XML

什么是 XML

  • XML(Extensible Markup Language)是一种可扩展标记语言
  • 语法简单,灵活性高,扩展性强
  • XML 文档的使用与操作系统、编程语言的开发平台无关
  • XML 的本质就是一个特殊格式的文本文档

XML 的作用

  • 数据存储
  • 配置文件
  • 数据交换

XML 的文档结构

声明部分

<?xml version="1.0" encoding="UTF-8"?>
  • <?xml:声明的开头
  • ?>:声明的结尾
  • version="1.0":表示该 xml 文档符合 1.0 的规范
  • encoding="UTF-8":表示该 xml 文档的编码模式为 UTF-8

内容部分

节点

  • xml 的内容部分主要由各种节点组成,节点又分为 标签节点注释节点文本节点 等

  • 每个 xml 文档必须有且有一个根标签节点

标签节点

开放式标签

开放式标签由 <...> 和 结束标签</...> 构成

<PhoneInfo></PhoneInfo>
  • <PhoneInfo>:起始标签
  • </PhoneInfo>:结束标签

自闭合标签

自闭合标签没有 结束标签,它是由 < 和 /> 构成

<Type name="P9"/>

标签属性

<Brand name="华为">
    <Type name="P9"/>
</Brand>
  • name="华为":属性,多个属性之间应该用空格隔开
  • name:属性名
  • "华为":属性值,属性值应该用 "" 或 '' 包裹

注释

xml 中的注释是由 <!-- 开始 和 --> 结束,中间的部分为注释内容

<!-- 手机列表 -->

文本节点

写在开放标签内部的文本内容即为 文本节点

<Type>P9</Type>

特殊字符处理

使用实体名称处理

<author>李明明 &amp; 王珊</author>
特殊字符实体名
< &lt;
> &gt;
" &quot;
' &apos;
& &amp;

使用 CDATA 节处理

<author><![CDATA[李明明 & 王珊]]></author>

XML 文档解析

使用 DOM 解析

读取 XML 文档

//获取解析器工厂
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
//获取解析器
DocumentBuilder builder = factory.newDocumentBuilder();
//获取DOM树
Document doc = builder.parse("收藏信息.xml");

获取节点对象

获取根节点

Element root = doc.getDocumentElement();

根据ID值获取节点

<Brand id="1">...</Brand>
Element ele = doc.getElementById("1");

根据标签名称获取节点

<Brand name="华为">...</Brand>
NodeList nodes = doc.getElementsByTagName("Brand");

根据标签名获取当前节点下的子节点

<PhoneInfo>
    <Brand name="华为">...</Brand>
    <Brand name="苹果">...</Brand>        
</PhoneInfo>
Element root = doc.getDocumentElement();
NodeList nodes = root.getElementsByTagName("Brand");

获取所有子节点

Element root = doc.getDocumentElement();
NodeList nodes = root.getChildNodes();

获取第一个子元素

Element root = doc.getDocumentElement();
Node firstNode = root.getFirstChild();

获取最后一个子元素

Element root = doc.getDocumentElement();
Node lastNode = root.getLastChild();

获取下一个同级元素

Element root = doc.getDocumentElement();
Node firstNode = root.getFirstChild();
Node nextNode = firstNode.getNextSibling();

获取上一个同级元素

Element root = doc.getDocumentElement();
Node lastNode = root.getLastChild();
Node preNode = lastNode.getPreviousSibling();

获取指定索引的节点

Element root = doc.getDocumentElement();
NodeList nodes = root.getChildNodes();
Node node = nodes.item(0);

获取父级节点

NodeList brands = doc.getElementsByTagName("Brand");
Node brand = brands.item(0);
Element brandEle = (Element)brand;
Node parentNode = brandEle.getParentNode();

获取节点信息

获取节点列表的长度

Element root = doc.getDocumentElement();
NodeList nodes = root.getChildNodes();
int leg = nodes.getLength();

获取节点的标签名

通过Element对象获取

Element root = doc.getDocumentElement();
Node firstNode = root.getFirstChild();
Element ele = (Element)firstNode;
String tagName = ele.getTagName();

通过Node对象获取

Element root = doc.getDocumentElement();
Node firstNode = root.getFirstChild();
String tagName = firstNode.getNodeName();

获取节点类型

Element root = doc.getDocumentElement();
Node node = root.getFirstChild();
short type = node.getNodeType();
if(type==Node.ELEMENT_NODE){
    System.out.println("标签节点");
}else if(type==Node.TEXT_NODE){
    System.out.println("文本节点");
}else if(type==Node.ATTRIBUTE_NODE){
    System.out.println("属性节点");
}else if(type==Node.COMMENT_NODE){
    System.out.println("注释节点");
}

获取文本节点的值

如果尝试获取非文本节点的值,则返回 null

Element root = doc.getDocumentElement();
Node firstNode = root.getFirstChild();
if(firstNode.getNodeType()==Node.TEXT_NODE){
    System.out.println(firstNode.getNodeValue());
}

操作节点

创建节点

Element ele = doc.createElement("Brand");

追加子节点

Element root = doc.getDocumentElement();
Element ele = doc.createElement("Brand");
root.appendChild(ele);

删除子节点

元素节点无法自己删除自己,只能先找到父级元素,然后由父级元素将自己删除

NodeList brands = doc.getElementsByTagName("Brand");
Node brand = brands.item(0);
Element brandEle = (Element)brand;
brandEle.getParentNode().removeChild(brandEle);

节点属性操作

获取指定属性的值

Element root = doc.getDocumentElement();
Node node = root.getFirstChild();
Element ele = (Element)node;
String attr = ele.getAttribute("name");

修改指定属性的值

NodeList brands = doc.getElementsByTagName("Brand");
for(int i=0;i<brands.getLength();i++){
    Node brand = brands.item(i);
    Element brandEle = (Element)brand;
    if(brandEle.getAttribute("name").equals("三星")){
        brandEle.setAttribute("name", "SAMSUNG");
    }
}

新增属性

Element ele = doc.createElement("Brand");
ele.setAttribute("name", "三星");

移除属性

Element root = doc.getDocumentElement();
Node node = root.getFirstChild();
Element ele = (Element)node;
ele.removeAttribute("name");

保存 XML 文档

//创建转换工厂
TransformerFactory factory = TransformerFactory.newInstance();
//创建转换器
Transformer former = factory.newTransformer();        
//创建DOM源
DOMSource xmlSource = new DOMSource(doc);
//创建XML文档流
StreamResult outputTarget = new StreamResult(new FileOutputStream("新的收藏信息.xml"));
//设置编码
former.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
//把DOM树转换为XML文件
former.transform(xmlSource, outputTarget);

使用 DOM4J 解析

导入依赖包

读取 XML 文档

SAXReader saxReader = new SAXReader();
Document doc = saxReader.read("收藏信息.xml");

获取节点对象

获取根节点

Element root = doc.getRootElement();

获取指定节点名的子节点,只返回第一个匹配的子节点

Element root = doc.getRootElement();
Element ele = root.element("member");

获取指定节点名的子节点,返回所有匹配的子节点

Element root = doc.getRootElement();
List eles = root.elements("member");

获取所有的子节点

Element root = doc.getRootElement();
List eles = root.elements();

获取子节点迭代器

Element root = doc.getRootElement();
Iterator iterator =root.elementIterator();
while(iterator.hasNext()){
    Element ele = (Element)iterator.next();
}

获取指定节点名的子节点迭代器

Element root = doc.getRootElement();
Iterator iterator =root.elementIterator("Brand");
while(iterator.hasNext()){
    Element ele = (Element)iterator.next();
}

获取指定ID的子元素

Element root = doc.getRootElement();
Element ele = root.elementByID("1");

获取父级元素

Element root = doc.getRootElement();
Element ele = root.element("member");
Element parentEle = ele.getParent();

获取节点信息

获取当前节点中的文本

Element root = doc.getRootElement();
Element ele = root.element("member");
String text = ele.getText();

获取根节点下指定子节点中的文本

Element root = doc.getRootElement();
String text = root.elementText("name");

操作节点

创建并追加节点

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");

删除节点

Element root = doc.getRootElement();
Element ele = root.element("member");
ele.getParent().remove(ele);

设置文本

Element root = doc.getRootElement();
Element ele = root.element("name");
ele.setText("张三");

节点属性操作

获取属性的值

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");
String brandStr = brandEle.attributeValue("name");

修改属性的值

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");
brandEle.addAttribute("name","小米");

添加属性

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");
brandEle.addAttribute("price","4000");

获取指定名称的属性对象

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");
Attribute attr = brandEle.attribute("name"); 

移除属性

Element root = doc.getRootElement();
Element brandEle = root.addElement("Brand");
Attribute attr = brandEle.attribute("name"); 
brandEle.remove(attr);

保存 XML 文档

OutputFormat format = OutputFormat.createPrettyPrint();
format.setEncoding("UTF-8");
XMLWriter writer = new XMLWriter(new FileWriter(path),format);
writer.write(doc);
writer.close();
posted @ 2021-06-09 12:22  编码小高  阅读(93)  评论(0编辑  收藏  举报