【Java 进阶篇】Java XML解析:从入门到精通

在这里插入图片描述

XML(可扩展标记语言)是一种常用的数据格式,用于存储和交换数据。在Java中,XML解析是一项重要的任务,它允许您从XML文档中提取和操作数据。本篇博客将从基础开始,详细介绍如何在Java中解析XML文档,包括DOM解析、SAX解析和StAX解析。无论您是XML的新手还是有一些经验的开发者,都能在本文中找到有关Java XML解析的有用信息。

为什么需要XML解析?

XML解析是将XML文档转换为应用程序可以理解和操作的数据的过程。它在许多应用程序中都具有关键作用,包括:

  • 数据交换:XML通常用于不同系统之间的数据交换,解析XML可将接收的数据转化为应用程序可以使用的格式。

  • 配置文件:XML通常用于存储应用程序的配置信息,解析XML可读取配置并将其应用到应用程序中。

  • Web服务:许多Web服务使用XML来传递数据,解析XML可用于访问和操作Web服务的响应数据。

  • 日志文件:某些应用程序将日志数据存储为XML,解析XML可用于分析和提取有关应用程序性能和行为的信息。

XML基础

在开始学习XML解析之前,让我们先了解XML的基础知识。

1. XML文档结构

XML文档由标签(element)、属性(attribute)、文本内容和注释组成。一个简单的XML文档包括以下部分:

<person age="30"><name>John</name><address><city>New York</city><zip>10001</zip></address>
</person>
  • <person> 是一个元素,带有一个名为 age 的属性和子元素 nameaddress
  • <name><address> 也是元素,分别包含文本内容。
  • age<person> 元素的属性。

2. XML解析模型

Java中有几种用于XML解析的模型,主要包括DOM、SAX和StAX。

  • DOM(文档对象模型):DOM解析将整个XML文档加载到内存中,形成一个树状结构,允许您轻松地遍历和操作XML数据。DOM解析适用于小型XML文档,但可能在处理大型文档时占用大量内存。

  • SAX(简单API for XML):SAX解析是事件驱动的,逐行读取XML文档,触发事件来处理元素和数据。SAX解析适用于大型XML文档,因为它不需要将整个文档加载到内存中。

  • StAX(流API for XML):StAX解析是一种双向解析模型,允许您以类似流的方式读取和写入XML数据。它是一种高性能的解析模型,适用于大型文档。

使用DOM解析XML

DOM解析是一种将整个XML文档加载到内存中并构建树状结构的解析方式。它允许您轻松地遍历和操作XML数据。

示例:解析XML文档

让我们通过一个示例来演示如何使用DOM解析XML文档。我们将解析以下XML文档:

<employees><employee><name>John</name><position>Manager</position></employee><employee><name>Alice</name><position>Engineer</position></employee>
</employees>
import javax.xml.parsers.*;
import org.w3c.dom.*;
import java.io.*;public class DOMParserExample {public static void main(String[] args) {try {// 创建一个DocumentBuilderDocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();DocumentBuilder builder = factory.newDocumentBuilder();// 解析XML文件Document document = builder.parse(new File("employees.xml"));// 获取根元素Element root = document.getDocumentElement();// 获取所有employee元素NodeList employeeList = root.getElementsByTagName("employee");for (int i = 0; i < employeeList.getLength(); i++) {Element employee = (Element) employeeList.item(i);// 获取name元素的文本内容String name = employee.getElementsByTagName("name").item(0).getTextContent();// 获取position元素的文本内容String position = employee.getElementsByTagName("position").item(0).getTextContent();System.out.println("Employee Name: " + name);System.out.println("Position: " + position);System.out.println("---------------");}} catch (Exception e) {e.printStackTrace();}}
}

在上述示例中,我们使用DocumentBuilderFactory创建一个DocumentBuilder,然后使用builder.parse()方法解析XML文件。接下来,我们获取根元素employees,并遍历所有employee元素,提取nameposition元素的文本内容。

示例:创建XML文档

DOM解析还允许您创建XML文档。以下是一个示例,演示如何使用DOM创建XML文档:

import javax.xml.parsers.*;
import org.w3c.dom.*;
import java.io.*;public class DOMCreateExample {public static void main(String[] args) {try {// 创建一个DocumentBuilderDocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();DocumentBuilder builder = factory.newDocumentBuilder();// 创建一个新文档Document document = builder.newDocument();// 创建根元素Element employees = document.createElement("employees");document.appendChild(employees);// 创建第一个employee元素Element employee1 = document.createElement("employee");employees.appendChild(employee1);Element name1 = document.createElement("name");name1.appendChild(document.createTextNode("John"));employee1.appendChild(name1);Element position1 = document.createElement("position");position1.appendChild(document.createTextNode("Manager"));employee1.appendChild(position1);// 创建第二个employee元素Element employee2 = document.createElement("employee");employees.appendChild(employee2);Element name2 = document.createElement("name");name2.appendChild(document.createTextNode("Alice"));employee2.appendChild(name2);Element position2 = document.createElement("position");position2.appendChild(document.createTextNode("Engineer"));employee2.appendChild(position2);// 将文档写入文件TransformerFactory transformerFactory = TransformerFactory.newInstance();Transformer transformer = transformerFactory.newTransformer();DOMSource source = new DOMSource(document);StreamResult result = new StreamResult(new File("new_employees.xml"));transformer.transform(source, result);System.out.println("XML文档创建成功!");} catch (Exception e) {e.printStackTrace();}}
}

在上述示例中,我们创建了一个新的Document对象,并使用createElement方法创建元素。然后,我们将元素添加到文档中,最后使用Transformer将文档写入文件。这将创建一个新的XML文档。

使用SAX解析XML

SAX解析是一种基于事件的解析模型,逐行读取XML文档并触发事件来处理元素和数据。相比DOM,SAX解析不需要将整个文档加载到内存中,因此适用于大型XML文档。

示例:解析XML文档

让我们通过一个示例来演示如何使用SAX解析XML文档:

import org.xml.sax.*;
import org.xml.sax.helpers.DefaultHandler;
import java.io.*;public class SAXParserExample {public static void main(String[] args) {try {// 创建一个SAXParserSAXParserFactory factory = SAXParserFactory.newInstance();SAXParser parser = factory.newSAXParser();// 创建一个处理器DefaultHandler handler = new DefaultHandler() {private boolean inEmployee = false;private String name = null;private String position = null;public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {if (qName.equalsIgnoreCase("employee")) {inEmployee = true;}}public void endElement(String uri, String localName, String qName) throws SAXException {if (qName.equalsIgnoreCase("employee")) {inEmployee = false;System.out.println("Employee Name: " + name);System.out.println("Position: " + position);System.out.println("---------------");}}public void characters(char[] ch, int start, int length) throws SAXException {if (inEmployee) {String data = new String(ch, start, length);if (name == null) {name = data;} else {position = data;}}}};// 解析XML文件parser.parse(new File("employees.xml"), handler);} catch (Exception e) {e.printStackTrace();}}
}

在上述示例中,我们创建了一个SAXParser和一个事件处理器DefaultHandler。事件处理器在遇到元素的开始和结束以及字符数据时触发事件。我们实现了startElementendElementcharacters方法,以处理相应的事件。

示例:使用SAX解析器工厂

SAX解析也可以使用解析器工厂来创建解析器。以下是一个示例:

import org.xml.sax.*;
import org.xml.sax.helpers.DefaultHandler;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import java.io.*;public class SAXParserFactoryExample {public static void main(String[] args) {try {SAXParserFactory factory = SAXParserFactory.newInstance();SAXParser parser = factory.newSAXParser();DefaultHandler handler = new DefaultHandler() {// 与前面的示例相同};parser.parse(new File("employees.xml"), handler);} catch (Exception e) {e.printStackTrace();}}
}

这个示例与之前的示例相似,但它使用了解析器工厂来创建SAX解析器。

使用StAX解析XML

StAX解析是一种基于流的解析模型,允许您以类似流的方式逐行读取和写入XML数据。StAX解析是一种高性能的解析模型,适用于大型XML文档。

示例:解析XML文档

让我们通过一个示例来演示如何使用StAX解析XML文档:

import javax.xml.stream.*;
import java.io.*;public class StAXParserExample {public static void main(String[] args) {try {XMLInputFactory factory = XMLInputFactory.newInstance();XMLStreamReader reader = factory.createXMLStreamReader(new FileInputStream("employees.xml"));String currentElement = "";String name = "";String position = "";while (reader.hasNext()) {int event = reader.next();switch (event) {case XMLStreamConstants.START_ELEMENT:currentElement = reader.getLocalName();break;case XMLStreamConstants.CHARACTERS:String data = reader.getText();if ("name".equals(currentElement)) {name = data;} else if ("position".equals(currentElement)) {position = data;}break;case XMLStreamConstants.END_ELEMENT:if ("employee".equals(reader.getLocalName())) {System.out.println("Employee Name: " + name);System.out.println("Position: " + position);System.out.println("---------------");}break;}}reader.close();} catch (Exception e) {e.printStackTrace();}}
}

在上述示例中,我们使用XMLInputFactory创建一个XMLStreamReader,然后使用while循环逐行读取XML文档中的数据。我们跟踪当前元素的名称,并根据当前元素的内容提取nameposition的值。最后,我们在遇到</employee>元素时打印员工信息。

示例:使用StAX写入XML

StAX不仅可以用于解析XML,还可以用于创建XML文档。以下是一个示例,演示如何使用StAX创建XML文档:

import javax.xml.stream.*;
import java.io.*;public class StAXCreateExample {public static void main(String[] args) {try {XMLOutputFactory factory = XMLOutputFactory.newInstance();XMLStreamWriter writer = factory.createXMLStreamWriter(new FileWriter("new_employees.xml"));writer.writeStartDocument();writer.writeStartElement("employees");// 创建第一个employee元素writer.writeStartElement("employee");writer.writeStartElement("name");writer.writeCharacters("John");writer.writeEndElement();writer.writeStartElement("position");writer.writeCharacters("Manager");writer.writeEndElement();writer.writeEndElement();// 创建第二个employee元素writer.writeStartElement("employee");writer.writeStartElement("name");writer.writeCharacters("Alice");writer.writeEndElement();writer.writeStartElement("position");writer.writeCharacters("Engineer");writer.writeEndElement();writer.writeEndElement();writer.writeEndElement();writer.writeEndDocument();writer.close();System.out.println("XML文档创建成功!");} catch (Exception e) {e.printStackTrace();}}
}

在上述示例中,我们使用XMLOutputFactory创建一个XMLStreamWriter,然后使用write方法逐步创建XML文档。我们首先写入文档声明,然后创建根元素employees,并添加两个employee元素,每个元素都包含nameposition元素。

选择合适的解析方法

在选择XML解析方法时,需要考虑以下因素:

  • 内存消耗:DOM解析通常需要将整个文档加载到内存中,可能导致内存消耗过大。SAX和StAX解析逐行读取文档,内存消耗较低。

  • 性能:SAX和StAX解析通常比DOM解析更快,尤其是在处理大型文档时。

  • 复杂性:DOM解析通常更容易编写,因为它允许您轻松地遍历和操作文档。SAX和StAX解析更复杂,因为您需要编写事件处理器来处理元素和数据。

  • 灵活性:如果您需要读取和写入XML,StAX解析是一种更灵活的选择,因为它支持双向操作。

根据您的具体需求,选择合适的解析方法非常重要。如果您需要处理小型文档并且希望方便地操作数据,DOM解析可能是不错的选择。如果您需要处理大型文档或需要更高的性能,SAX或StAX解析可能更适合。

XML解析库

Java提供了许多XML解析库,用于简化XML解析的过程。一些常见的XML解析库包括:

  • JDOM:JDOM是一种用于解析和操作XML的流行库,提供了简单的API。

  • DOM4J:DOM4J是一个基于DOM的XML解析库,具有强大的功能和性能。

  • Jsoup:Jsoup是一种用于解析HTML和XML的库,通常用于Web抓取和数据提取。

  • Jackson:Jackson是一个处理JSON的库,但也可以用于处理XML。

这些库提供了不同的功能和性能特点,您可以根据自己的需求选择最合适的库。

使用XML Schema验证

除了解析XML,还可以使用XML Schema(XSD)来验证XML文档的有效性。XML Schema定义了XML文档的结构和数据类型,可以确保文档符合规定的结构。

以下是一个使用XSD验证XML的示例:

import javax.xml.XMLConstants;
import javax.xml.transform.Source;
import javax.xml.transform.stream.StreamSource;
import javax.xml.validation.Schema;
import javax.xml.validation.SchemaFactory;
import javax.xml.validation.Validator;
import org.xml.sax.SAXException;
import java.io.File;
import java.io.IOException;public class XsdValidatorExample {public static void main(String[] args) {try {String xmlFile = "employees.xml";String xsdFile = "employees.xsd";SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI);Schema schema = factory.newSchema(new File(xsdFile));Validator validator = schema.newValidator();Source source = new StreamSource(new File(xmlFile));validator.validate(source);System.out.println("XML验证通过!");} catch (SAXException | IOException e) {System.out.println("XML验证错误: " + e.getMessage());}}
}

在上述示例中,我们使用SchemaFactory创建一个Schema对象,该对象包含了我们之前定义的XSD约束。然后,我们使用Validator来验证XML文档。如果XML文档不符合XSD的约束,将抛出相应的错误。

实际应用示例

让我们来看一个实际的应用示例:使用XML解析来处理Web服务的响应。假设您正在开发一个应用程序,通过调用Web服务来获取数据。 Web服务通常以XML形式返回数据,您可以使用XML解析来提取和处理Web服务的响应。

import java.io.StringReader;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;public class WebServiceExample {public static void main(String[] args) {// 假设这是Web服务的响应XMLString responseXml = "<data><item>Item 1</item><item>Item 2</item></data>";try {// 创建一个DocumentBuilderDocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();DocumentBuilder builder = factory.newDocumentBuilder();// 解析Web服务的响应XMLDocument document = builder.parse(new InputSource(new StringReader(responseXml)));// 获取根元素Node root = document.getDocumentElement();// 获取所有item元素NodeList itemList = root.getChildNodes();for (int i = 0; i < itemList.getLength(); i++) {Node itemNode = itemList.item(i);if (itemNode.getNodeType() == Node.ELEMENT_NODE) {String item = itemNode.getTextContent();System.out.println("Item: " + item);}}} catch (Exception e) {e.printStackTrace();}}
}

在这个示例中,我们模拟了Web服务的响应XML,并使用DOM解析来提取item元素的文本内容。这可以在实际应用程序中用于处理Web服务的响应数据,提取所需的信息。

总结

本博客详细介绍了Java中的XML解析,包括DOM、SAX和StAX三种解析模型。您可以根据项目的需求选择最合适的解析方式。此外,我们还了解了如何使用XML Schema验证XML文档的有效性,以及一些常见的XML解析库。

XML解析是Java开发中常见的任务,它允许您与其他系统交换数据,读取和写入配置文件,访问Web服务的响应数据等。熟练掌握XML解析是Java开发中的一项重要技能。

希望本博客对您有所帮助,如果您有任何问题或需要进一步的指导,请随时提问。祝您在Java XML解析的学习和应用中取得成功!

作者信息

作者 : 繁依Fanyi
CSDN: https://techfanyi.blog.csdn.net
掘金:https://juejin.cn/user/4154386571867191

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/116926.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

前端AJAX入门到实战,学习前端框架前必会的(ajax+node.js+webpack+git)(二)

阳光总在风雨后&#xff0c;请相信有彩虹。 案例 - 图书管理 bootstrap弹框 需求&#xff0c;点击添加按钮&#xff0c;没有离开当前页面&#xff0c;在当前页面弹出弹框&#xff08;弹窗&#xff09; 先学着实现一个简单的弹框&#xff0c;如下图右下角 bootstrap有两种方式…

20231024后端研发面经整理

1.如何在单链表O(1)删除节点&#xff1f; 狸猫换太子 2.redis中的key如何找到对应的内存位置&#xff1f; 哈希碰撞的话用链表存 3.线性探测哈希法的插入&#xff0c;查找和删除 插入&#xff1a;一个个挨着后面找&#xff0c;知道有空位 查找&#xff1a;一个个挨着后面找…

gin 框架出现runtime error: index out of range [0] with length 0

之前是这样的&#xff1a; category : c.Request.Form["type"][0] 加上这一句就变成了 fmt.Println(c.Request.FormFile("type")) category : c.Request.Form["type"][0]

交换机/防火墙-基础配置-23.10.11

update 优化了目录逻辑 -10.24.2023 一.前置知识 1.MAC地址 交换机在给主机之间传递信息包时&#xff0c;通过MAC地址来标识每台主机 主机间发生信息包交换时&#xff0c;交换机就会将通信过的主机的mac地址存下 dis mac-address 交换机转发的数据包中&#xff0c;会包含一…

Java面试(JVM篇)——JVM 面试题合集 深入理解JVM虚拟机

关于什么是JVM&#xff1f; 作用&#xff1a; 运⾏并管理Java 源码⽂件所⽣成的Class⽂件&#xff0c;在不同的操作系统上安装不同的JVM &#xff0c;从⽽实现了跨平台的保证。 ⼀般情况下&#xff0c;对于开发者⽽⾔&#xff0c;即使不熟悉JVM 的运⾏机制并不影响业务代码的…

Spring+spring mvc+mybatis整合的框架

Spring是一个轻量级的企业级应用开发框架&#xff0c;于2004年由Rod Johnson发布了1.0版本&#xff0c;经过多年的更新迭代&#xff0c;已经逐渐成为Java开源世界的第一框架&#xff0c;Spring框架号称Java EE应用的一站式解决方案&#xff0c;与各个优秀的MVC框架如SpringMVC、…

Python(一)关键字、内置函数

程序员的公众号&#xff1a;源1024&#xff0c;获取更多资料&#xff0c;无加密无套路&#xff01; 最近整理了一波电子书籍资料&#xff0c;包含《Effective Java中文版 第2版》《深入JAVA虚拟机》&#xff0c;《重构改善既有代码设计》&#xff0c;《MySQL高性能-第3版》&am…

模拟 Junit 框架

需求 定义若干个方法&#xff0c;只要加了MyTest注解&#xff0c;就可以在启动时被触发执行 分析 定义一个自定义注解MyTest&#xff0c;只能注解方法&#xff0c;存活范围是一直都在定义若干个方法&#xff0c;只要有MyTest注解的方法就能在启动时被触发执行&#xff0c;没有这…

超强满血不收费的AI绘图教程来了(在线Stable Diffusion一键即用)

超强满血不收费的AI绘图教程来了&#xff08;在线Stable Diffusion一键即用&#xff09; 一、简介1.1 AI绘图1.2 Stable Diffusion1.2.1 原理简述1.2.2 应用流程 二、AI绘图工具2.1 吐司TusiArt2.2 哩布哩布LibLibAI2.3 原生部署 三、一键即用3.1 开箱尝鲜3.2 模型关联3.3 Cont…

Day7力扣打卡

打卡记录 合法分组的最少组数&#xff08;贪心&#xff09; 链接 举例说明&#xff0c;假设 c n t [ x ] 32 cnt[x]32 cnt[x]32&#xff0c; k 10 k10 k10&#xff0c;那么 32 10 10 10 2 321010102 321010102&#xff0c;多出的 2 2 2 可以分成两个 1 1 1&#xf…

记一次gitlab平台任意用户注册引发的源代码泄漏

文章目录 一、漏洞原因二、漏洞利用1、任意用户注册2、成功进入后台3、越权查看其他用户的仓库源代码4、发现源代码仓库泄漏5、通讯录的地方,发现账号泄漏泄漏三、漏洞进一步利用四、总结五、免责声明一、漏洞原因 可以任意注册账号通过越权,查看其他用户仓库内的源代码造成源…

小白必看,手把手教你重装系统

一&#xff0c;安装步骤 二&#xff0c;重装之前需要做的准备 1、重装之前请大家务必注意备份重要资料。电脑有价&#xff0c;数据无价——重要数据备份之后&#xff0c;电脑随便折腾都没问题。大不了就是重装不成功。系统软件问题多试几次总能解决的&#xff0c;但重要数据一…

前端性能优化 - 虚拟滚动

一 需求背景 需求&#xff1a;在一个表格里面一次性渲染全部数据&#xff0c;不采用分页形式&#xff0c;每行数据都有Echart图插入。 问题&#xff1a;图表渲染卡顿 技术栈&#xff1a;Vue、Element UI 卡顿原因&#xff1a;页面渲染时大量的元素参与到了重排的动作中&#x…

MySQL数据库(三)

文章目录 MySQL数据库一、约束条件二、约束条件之主键三、补充一些其它SQL语句四、表查找关键字Select与from五、查询关键字之where筛选六、查询关键字之group by分组七、分组补充函数八、关键字之having过滤九、关键字之distinct去重十、关键字之order by排序十一、关键字之li…

苹果开发者 Xcode发布TestFlight全流程

打包前注意事项 使用Xcode导出安装包之前&#xff0c;必须先确认账户的所有合约是否全部同意&#xff0c;如果有不同意的&#xff0c;在出包的时候会弹出报错 点击前往苹果开发者官网https://appstoreconnect.apple.com/agreements/ 登录自己的开发者账户后&#xff0c;可以看…

react项目实现文件预览,比如PDF、txt、word、Excel、ppt等常见文件(腾讯云cos)

使用腾讯云文档预览&#xff0c;需要开通文档预览功能&#xff0c;该功能需要收费的。 使用限制 如果需要图片预览、视频或音频可以使用获取下载链接。 页面代码 <button onClick() > {handleClick(myself/文档.xlsx)}>预览</button><div style{{ height:…

谈谈你对spring boot 3.0的理解

谈谈你对spring boot 3.0的理解 一&#xff0c;Spring Boot 3.0 的兼容性 Spring Boot 3.0 在兼容性方面做出了很大的努力&#xff0c;以支持存量项目和老项目。尽管如此&#xff0c;仍需注意以下几点&#xff1a; Java 版本要求&#xff1a;Spring Boot 3.0 要求使用 Java 1…

Boundary-Aware RGBD Salient Object Detection With Cross-Modal Feature Sampling

方法 体会 实验做得比较详细&#xff0c;但未公布代码

浏览器标签上添加icon图标;html引用ico文件

实例 <link rel"shortcut icon" href"./XXX.ico" type"image/x-icon">页面和图标在同一目录内 则 <link rel"shortcut icon" type"text/css" href"study.ico"/>可以阿里矢量图库关键字搜索下载自己…