0

0

Java基础系列17:使用DOM、SAX、JDOM、DOM4J解析XML文件详解

高洛峰

高洛峰

发布时间:2016-10-13 15:57:12

|

1992人浏览过

|

来源于php中文网

原创

一 简介

在java中,可以使用多种方式来解析xml文件,其中最常见的可能就是dom、sax、jdom、dom4j这四种方式了。其中,dom和sax这两种解析xml文件的方式有jdk自带的api,因此不需要额外引入第三方的jar包。与之相反的是,jdom和dom4j这两种解析方式都是第三方开源项目,因此在使用这两种方式解析xml文件时需要额外引入相关jar包

(1)DOM

DOM是用与平台和语言无关的方式表示XML文档的官方W3C标准。DOM是以层次结构组织的节点或信息片断的集合,这个层次结构允许开发人员在树中寻找特定信息。分析该结构通常需要加载整个文档和构造层次结构,然后才能做任何工作

因此在使用DOM这种方式来解析XML文件时,解析器需要将整个XML文件读到内存中,形成一个树形结构方便后面的操作

优点: 整个文档树在内存中,便于操作;支持删除、修改、重新排列等多种操作

立即学习Java免费学习笔记(深入)”;

缺点: 将整个文档调入内存(包括无用的节点),浪费时间和内存,如果XML过大容易出现内存溢出问题

(2)SAX

由于DOM解析XML文件时需要一次性读入整个文件,当文件过大时有诸多不足之处,因此为了解决这个问题,出现了SAX这种基于事件驱动的解析方式

SAX解析XML文件通过从上往下依次不断载入内容到内存中,当解析器发现元素的开始标志、结束标志、文本、文档的开始标志、文档的结束标志等相关标志时,将会触发一些对应的事件,我们需要做的就是在这些事件的方法中编写自定义代码,用于保存获取到的数据

优点:不用事先载入整个文档,占用资源(内存)少;使用SAX方式解析编写的代码要比使用DOM解析编写的代码少

缺点:不是持久的;事件过后,若没保存数据,那么数据就丢了;无状态性;从事件中只能得到文本,但不知该文本属于哪个元素

(3)JDOM

使用JDOM来解析XML文件跟使用DOM来解析从代码上来说解析思路是差不多的。JDOM与DOM主要有两方面不同:首先,JDOM仅使用具体类而不使用接口,这在某些方面简化了API,但是也限制了灵活性。其次是JDOM的API大量使用了Collections类,简化了那些已经熟悉这些类的Java开发者的使用

优点:开源项目;比DOM容易理解

缺点:JDOM自身不包含解析器。它通常使用SAX2解析器来解析和验证输入XML文档

(4)DOM4J

DOM4J 是一个非常非常优秀的Java XML API,具有性能优异、功能强大和极端易用使用的特点,同时它也是一个开放源代码的软件。如今你可以看到越来越多的 Java 软件都在使用 DOM4J 来读写 XML

由于DOM4J无论在性能方面还是代码编写方面都是很强大的,特别是当XML文件很大时使用DOM4J来解析也会有较高的效率。因此,建议平时需要解析XML文件可以考虑尽可能使用DOM4J来解析。当然如果文件非常小的话使用DOM来解析也是可以的

优点:

开源项目

DOM4J是JDOM的一种智能分支,它合并了需要超出基本XML文档的功能

具有性能优异、灵活性好、简单易用等特点

二 DOM解析XML文件

(1)在进行代码编写测试之前,需要准备一个XML文件,我这里准备的文件是:demo1.xml

demo1.xml:

<?xml  version="1.0" encoding="UTF-8" ?>
<employees>
    <user>
        <name>zifangsky</name>
        <age>10</age>
        <sex>male</sex>
        <contact>https://www.zifangsky.cn</contact>
    </user>
    <user>
        <name>admin</name>
        <age>20</age>
        <sex>male</sex>
        <contact>https://www.tar.pub</contact>
    </user>
</employees>

(2)代码实例:

package cn.zifangsky.xml;
 
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
 
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;
 
public class DomParseTest {
 
    public static void main(String[] args) {
        DocumentBuilderFactory dFactory = DocumentBuilderFactory.newInstance();
        try {
            DocumentBuilder dBuilder = dFactory.newDocumentBuilder();
            // 加载一个xml文件
            Document document = dBuilder
                    .parse("src/cn/zifangsky/xml/demo1.xml");
            // 获取user节点集合
            NodeList userList = document.getElementsByTagName("user");
            int userListLength = userList.getLength();
            System.out.println("此xml文件一共有" + userListLength + "个'user'节点\n");
 
            // 遍历
            for (int i = 0; i <p>从上面的代码可以看出,在使用DOM来解析XML文件时一般需要做以下几步操作:</p><p>创建一个文档构建器工厂(DocumentBuilderFactory)实例</p><p>通过上面的DocumentBuilderFactory生成一个新的文档构建器(DocumentBuilder)</p><p>使用上面的DocumentBuilder解析(parse)一个XML文件,生成文档树(Document)</p><p>通过Document获取指定id的节点或根据节点名获取所有符合条件的节点集合</p><p>遍历每个节点,可以获取该节点的属性、属性值等相关参数</p><p>如果该节点还存在子节点,可以根据上面的方式继续遍历它的所有子节点</p><p>(3)上面的代码输出如下:</p><pre class="brush:java;toolbar:false">此xml文件一共有2个'user'节点
 
'user'节点0有1个属性:
属性0: 属性名: id ,属性值: 1
属性为'id'的对应值是: 1
 
该节点一共有9个子节点,分别是:
节点名: name,节点值: zifangsky
节点名: age,节点值: 10
节点名: sex,节点值: male
节点名: contact,节点值: https://www.zifangsky.cn
***************************
'user'节点1有1个属性:
属性0: 属性名: id ,属性值: 2
属性为'id'的对应值是: 2
 
该节点一共有9个子节点,分别是:
节点名: name,节点值: admin
节点名: age,节点值: 20
节点名: sex,节点值: male
节点名: contact,节点值: https://www.tar.pub
***************************

三 SAX解析XML文件

在进行本次测试时,并不引入其他XML文件,仍然使用上面的demo1.xml文件

由于SAX解析XML文件跟DOM不同,它并不是将整个文档都载入到内存中。解析器在解析XML文件时,通过逐步载入文档,从上往下一行行的解析XML文件,在碰到文档开始标志、节点开始标志、文本文档、节点结束标志、文档结束标志时进行对应的事件处理。因此,我们首先需要构造一个这样的解析处理器来申明:当解析到这些标志时,我们需要进行怎样的自定义处理

(1)解析处理器SAXParseHandler.java:

package cn.zifangsky.xml;
 
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;
 
public class SAXParseHandler extends DefaultHandler {
 
    /**
     * 用来遍历XML文件的开始标签
     * */
    @Override
    public void startElement(String uri, String localName, String qName,
            Attributes attributes) throws SAXException {
        super.startElement(uri, localName, qName, attributes);
         
        //解析'user'元素的属性值
//      if(qName.equals("user"))
//          System.out.println("'user'元素的id属性值是:" + attributes.getValue("id"));
         
        //遍历并打印元素的属性
        int length = attributes.getLength();
        if(length > 0){
            System.out.println("元素'" + qName + "'的属性是:");
             
            for(int i=0;i<length>");
 
    }
 
    /**
     * 用来遍历XML文件的结束标签
     * */
    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        super.endElement(uri, localName, qName);
         
        System.out.println("");
    }
     
    /**
     * 文本内容
     * */
    public void characters(char[] ch, int start, int length)
            throws SAXException {
        super.characters(ch, start, length);
        String value = new String(ch, start, length).trim();
        if(!value.equals(""))
            System.out.print(value);
    }
 
    /**
     * 用来标识解析开始
     * */
    @Override
    public void startDocument() throws SAXException {
        System.out.println("SAX解析开始");
        super.startDocument();
    }
     
    /**
     * 用来标识解析结束
     * */
    @Override
    public void endDocument() throws SAXException {
        System.out.println("SAX解析结束");
        super.endDocument();
    }
 
}</length>

关于上面代码的一些含义我这里就不再做解释了,可以自行参考注释内容

(2)测试:

SAXParseTest.java文件:

package cn.zifangsky.xml;
 
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
 
public class SAXParseTest {
 
    public static void main(String[] args) {
        SAXParserFactory sFactory = SAXParserFactory.newInstance();
        try {
            SAXParser saxParser = sFactory.newSAXParser();
            //创建自定义的SAXParseHandler解析类
            SAXParseHandler saxParseHandler = new SAXParseHandler();
            saxParser.parse("src/cn/zifangsky/xml/demo1.xml", saxParseHandler);
 
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
 
}

从上面的代码可以看出,使用SAX解析XML文件时,一共传递进去了两个参数,分别是:XML文件路径和前面定义的解析处理器。有了具体的XML文件以及对应的处理器来处理对应的标志事情,因此SAX这种解析方式就可以顺利地进行解析工作了

VisualizeAI
VisualizeAI

用AI把你的想法变成现实

下载

(3)上面测试的输出如下:

SAX解析开始
<employees>元素'user'的属性是:
    属性名:id,属性值: 1
 
<user><name>zifangsky<name></name>
<age>10<age></age>
<sex>male<sex></sex>
<contact>https://www.zifangsky.cn<contact></contact>
<user></user>
元素'user'的属性是:
    属性名:id,属性值: 2
 
<user><name>admin<name></name>
<age>20<age></age>
<sex>male<sex></sex>
<contact>https://www.tar.pub<contact></contact>
<user></user>
<employees></employees>
SAX解析结束</contact></sex></age></name></user></contact></sex></age></name></user></employees>

四 JDOM解析XML文件

跟前面两种解析方式不同的是,使用JDOM来解析XML文件需要下载额外的jar包

(1)下载jar包并导入到项目中:

下载地址:http://www.jdom.org/downloads/index.html

目前最新版本是:JDOM 2.0.6

然后将下载得到的“jdom-2.0.6.jar”文件导入到测试项目中

注:关于如何在一个Java项目中导入额外的jar,这里将不多做解释,不太会的童鞋可以自行百度

(2)测试代码:

JDOMTest.java:

package cn.zifangsky.xml;
 
import java.util.List;
 
import org.jdom2.Document;
import org.jdom2.Element;
import org.jdom2.input.SAXBuilder;
 
public class JDOMTest {
 
    /**
     * @param args
     */
    public static void main(String[] args) {
        SAXBuilder saxBuilder = new SAXBuilder();
        try {
            Document document = saxBuilder.build("src/cn/zifangsky/xml/demo1.xml");
             
            //获取XML文件的根节点
            Element rootElement = document.getRootElement();
//          System.out.println(rootElement.getName());
            List<element> usersList = rootElement.getChildren();  //获取子节点
            for(Element u : usersList){
//              List<attribute> attributes = u.getAttributes();
//              for(Attribute attribute : attributes){
//                  System.out.println("属性名:" + attribute.getName() + ",属性值:" + attribute.getValue());
//              }
                System.out.println("'id'的值是: " + u.getAttributeValue("id"));
            }
             
             
        }catch (Exception e) {
            e.printStackTrace();
        }
 
    }
 
}</attribute></element>

从上面的代码可以看出,使用JDOM来解析XML文件,主要需要做以下几个步骤:

新建一个SAXBuilder

通过SAXBuilder的build方法传入一个XML文件的路径得到Document

通过Document的getRootElement方法获取根节点

通过getChildren方法获取根节点的所有子节点

然后是遍历每个子节点,获取属性、属性值、节点名、节点值等内容

如果该节点也有子节点,然后同样可以通过getChildren方法获取该节点的子节点

后面的步骤跟上面一样,不断递归到文本节点截止

(3)上面测试的输出如下:

'id'的值是: 1
'id'的值是: 2

五 DOM4J解析XML文件

jar包下载地址:https://sourceforge.net/projects/dom4j/files/

同样,在使用DOM4J解析XML文件时需要往项目中引入“dom4j-1.6.1.jar”文件

(1)一个简单实例:

i)DOM4JTest.java:

package cn.zifangsky.xml;
 
import java.io.File;
import java.util.Iterator;
import java.util.List;
 
import org.dom4j.Attribute;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
 
public class DOM4JTest {
 
    public static void main(String[] args) {
        SAXReader reader = new SAXReader();
        try {
            Document document = reader.read(new File("src/cn/zifangsky/xml/demo1.xml"));
            //获取XML文件的根节点
            Element rootElement = document.getRootElement();
            System.out.println(rootElement.getName());
             
            //通过elementIterator方法获取迭代器
            Iterator<element> iterator = rootElement.elementIterator();
            //遍历
            while(iterator.hasNext()){
                Element user = iterator.next();
                //获取属性并遍历
                List<attribute> aList = user.attributes();
             
                for(Attribute attribute : aList){
                    System.out.println("属性名:" + attribute.getName() + ",属性值:" + attribute.getValue());
                }
                 
                //子节点
                Iterator<element> childList = user.elementIterator();
                while(childList.hasNext()){
                    Element child = childList.next();
//                  System.out.println(child.getName() + " : " + child.getTextTrim());
                    System.out.println(child.getName() + " : " + child.getStringValue());
                }
            }
         
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
 
}</element></attribute></element>

从上面的代码可以看出,跟前面的JDOM解析方式流程是差不多的,并且关键地方也有注释,因此这里就不多做解释了

ii)上面的代码输出如下:

employees
属性名:id,属性值:1
name : zifangsky
age : 10
sex : male
contact : https://www.zifangsky.cn
属性名:id,属性值:2
name : admin
age : 20
sex : male
contact : https://www.tar.pub

(2)将XML文件解析成Java对象:

i)为了方便测试,这里准备一个新的XML文件:

demo2.xml:

<?xml  version="1.0" encoding="UTF-8" ?>
<user>
    <name>zifangsky</name>
    <age>100</age>
    <sex>男</sex>
    <contact>https://www.zifangsky.cn</contact>
    <ownpet>旺财</ownpet>
    <ownpet>九头猫妖</ownpet>
</user>

ii)同时准备一个Java实体类,恰好跟上面的XML文件中的属性相对应:

User.java:

package cn.zifangsky.xml;
 
import java.util.List;
 
public class User {
    private String name;
    private String sex;
    private int age;
    private String contact;
    private List<string> ownPet;
 
    public String getName() {
        return name;
    }
 
    public void setName(String name) {
        this.name = name;
    }
 
    public String getSex() {
        return sex;
    }
 
    public void setSex(String sex) {
        this.sex = sex;
    }
 
    public int getAge() {
        return age;
    }
 
    public void setAge(int age) {
        this.age = age;
    }
 
    public String getContact() {
        return contact;
    }
 
    public void setContact(String contact) {
        this.contact = contact;
    }
 
    protected List<string> getOwnPet() {
        return ownPet;
    }
 
    protected void setOwnPet(List<string> ownPet) {
        this.ownPet = ownPet;
    }
 
    @Override
    public String toString() {
        return "User [name=" + name + ", sex=" + sex + ", age=" + age
                + ", contact=" + contact + ", ownPet=" + ownPet + "]";
    }
}</string></string></string>

iii)测试代码:

XMLtoJava.java:

package cn.zifangsky.xml;
 
import java.io.File;
import java.util.ArrayList;
import java.util.List;
 
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
 
public class XMLtoJava {
 
    public User parseXMLtoJava(String xmlPath){
        User user = new User();
        List<string> ownPet = new ArrayList<string>();
         
        SAXReader saxReader = new SAXReader();
        try {
            Document document = saxReader.read(new File(xmlPath));
            Element rootElement = document.getRootElement();  //获取根节点
             
            List<element> children = rootElement.elements();  //获取根节点的子节点
            //遍历
            for(Element child : children){
                String elementName = child.getName();  //节点名
                String elementValue = child.getStringValue();  //节点值
                switch (elementName) {
                case "name":
                    user.setName(elementValue);
                    break;
                case "sex":
                    user.setSex(elementValue);
                    break; 
                case "age":
                    user.setAge(Integer.valueOf(elementValue));
                    break;
                case "contact":
                    user.setContact(elementValue);
                    break; 
                case "ownPet":
                    ownPet.add(elementValue);
                    break; 
                default:
                    break;
                }
     
            }
            user.setOwnPet(ownPet);
 
        } catch (Exception e) {
            e.printStackTrace();
        }
        return user;
    }
     
    public static void main(String[] args) {
        XMLtoJava demo = new XMLtoJava();
        User user = demo.parseXMLtoJava("src/cn/zifangsky/xml/demo2.xml");
        System.out.println(user);
    }
 
}</element></string></string>

经过前面的分析之后,上面这个代码也是很容易理解的:通过遍历节点,如果节点名跟Java类中的某个属性名相对应,那么就将节点值赋值给该属性

iv)上面的代码输出如下:

User [name=zifangsky, sex=男, age=100, contact=https://www.zifangsky.cn, ownPet=[旺财, 九头猫妖]]

(3)解析一个XML文件并尽可能原样输出:

DOM4JTest2:

package cn.zifangsky.xml;
 
import java.io.File;
import java.util.List;
 
import org.dom4j.Attribute;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
 
public class DOM4JTest2 {
 
    /**
     * 解析XML文件并尽可能原样输出
     * 
     * @param xmlPath
     *            待解析的XML文件路径
     * @return null
     * */
    public void parse(String xmlPath) {
        SAXReader saxReader = new SAXReader();
        try {
            Document document = saxReader.read(new File(xmlPath));
            Element rootElement = document.getRootElement();
 
            print(rootElement, 0);
 
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
 
    /**
     * 打印一个XML节点的详情
     * 
     * @param element
     *            一个XML节点
     * @param level
     *            用于判断xml节点前缩进多少的标识,每深入一层则多输出4个空格
     * @return null
     * */
    public void print(Element element, int level) {
        List<element> elementList = element.elements(); // 当前节点的子节点List
 
        // 空格
        StringBuffer spacebBuffer = new StringBuffer("");
        for (int i = 0; i  attributes = element.attributes();
        for (Attribute attribute : attributes)
            System.out.print(" " + attribute.getName() + "=\""
                    + attribute.getText() + "\"");
 
        // 有子节点
        if (elementList.size() > 0) {
            System.out.println(">");
            // 遍历并递归
            for (Element child : elementList) {
                print(child, level + 1);
            }
            // 输出结束节点
            System.out.println(space + "" + element.getName() + ">");
 
        } else {
            // 如果节点没有文本则简化输出
            if (element.getStringValue().trim().equals(""))
                System.out.println(" />");
            else
                System.out.println(">" + element.getStringValue() + ""
                        + element.getName() + ">");
        }
 
    }
 
    public static void main(String[] args) {
        DOM4JTest2 test2 = new DOM4JTest2();
        test2.parse("src/cn/zifangsky/xml/demo3.xml");
 
    }
 
}</element>

这段代码同样没有什么新的东西,原理就是利用递归来不断进行解析输出,注意一下不同层次的节点的缩进即可。刚开始测试时建议用一些结构比较简单的代码,如上面的demo1.xml和demo2.xml文件。在测试没问题时可以选择一些复杂的XML文件来测试是否能够正常输出,比如:

demo3.xml:

<?xml  version="1.0" encoding="UTF-8"?>
<application>
    <grammars></grammars>
    <resources>
        <resource>
            <resource>
                <method>
                    <request>
                        <representation></representation>
                    </request>
                    <response>
                        <representation>
                            <param>
                        </representation>
                        <representation>
                            <param>
                        </representation>
                    </response>
                </method>
            </resource>
            <resource>
                <method>
                    <request>
                        <representation>
                            <param>
                        </representation>
                    </request>
                    <response>
                        <representation></representation>
                        <representation></representation>
                    </response>
                </method>
            </resource>
        </resource>
    </resources>
</application>

为什么我在标题上说的是尽可能原样输出,其原因就是上面那段解析代码在碰到下面这种XML节点时,输出就不一样了:

<creator></creator>
<category></category>
<category></category>
<category></category>

这段XML文档节点最后输出如下:

<creator>admin</creator>
<category>运维</category>
<category>zabbix</category>
<category>端口</category>


java速学教程(入门到精通)
java速学教程(入门到精通)

java怎么学习?java怎么入门?java在哪学?java怎么学才快?不用担心,这里为大家提供了java速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
Golang 测试体系与代码质量保障:工程级可靠性建设
Golang 测试体系与代码质量保障:工程级可靠性建设

Go语言测试体系与代码质量保障聚焦于构建工程级可靠性系统。本专题深入解析Go的测试工具链(如go test)、单元测试、集成测试及端到端测试实践,结合代码覆盖率分析、静态代码扫描(如go vet)和动态分析工具,建立全链路质量监控机制。通过自动化测试框架、持续集成(CI)流水线配置及代码审查规范,实现测试用例管理、缺陷追踪与质量门禁控制,确保代码健壮性与可维护性,为高可靠性工程系统提供质量保障。

43

2026.02.28

Golang 工程化架构设计:可维护与可演进系统构建
Golang 工程化架构设计:可维护与可演进系统构建

Go语言工程化架构设计专注于构建高可维护性、可演进的企业级系统。本专题深入探讨Go项目的目录结构设计、模块划分、依赖管理等核心架构原则,涵盖微服务架构、领域驱动设计(DDD)在Go中的实践应用。通过实战案例解析接口抽象、错误处理、配置管理、日志监控等关键工程化技术,帮助开发者掌握构建稳定、可扩展Go应用的最佳实践方法。

38

2026.02.28

Golang 性能分析与运行时机制:构建高性能程序
Golang 性能分析与运行时机制:构建高性能程序

Go语言以其高效的并发模型和优异的性能表现广泛应用于高并发、高性能场景。其运行时机制包括 Goroutine 调度、内存管理、垃圾回收等方面,深入理解这些机制有助于编写更高效稳定的程序。本专题将系统讲解 Golang 的性能分析工具使用、常见性能瓶颈定位及优化策略,并结合实际案例剖析 Go 程序的运行时行为,帮助开发者掌握构建高性能应用的关键技能。

35

2026.02.28

Golang 并发编程模型与工程实践:从语言特性到系统性能
Golang 并发编程模型与工程实践:从语言特性到系统性能

本专题系统讲解 Golang 并发编程模型,从语言级特性出发,深入理解 goroutine、channel 与调度机制。结合工程实践,分析并发设计模式、性能瓶颈与资源控制策略,帮助将并发能力有效转化为稳定、可扩展的系统性能优势。

20

2026.02.27

Golang 高级特性与最佳实践:提升代码艺术
Golang 高级特性与最佳实践:提升代码艺术

本专题深入剖析 Golang 的高级特性与工程级最佳实践,涵盖并发模型、内存管理、接口设计与错误处理策略。通过真实场景与代码对比,引导从“可运行”走向“高质量”,帮助构建高性能、可扩展、易维护的优雅 Go 代码体系。

18

2026.02.27

Golang 测试与调试专题:确保代码可靠性
Golang 测试与调试专题:确保代码可靠性

本专题聚焦 Golang 的测试与调试体系,系统讲解单元测试、表驱动测试、基准测试与覆盖率分析方法,并深入剖析调试工具与常见问题定位思路。通过实践示例,引导建立可验证、可回归的工程习惯,从而持续提升代码可靠性与可维护性。

3

2026.02.27

漫蛙app官网链接入口
漫蛙app官网链接入口

漫蛙App官网提供多条稳定入口,包括 https://manwa.me、https

235

2026.02.27

deepseek在线提问
deepseek在线提问

本合集汇总了DeepSeek在线提问技巧与免登录使用入口,助你快速上手AI对话、写作、分析等功能。阅读专题下面的文章了解更多详细内容。

11

2026.02.27

AO3官网直接进入
AO3官网直接进入

AO3官网最新入口合集,汇总2026年可用官方及镜像链接,助你快速稳定访问Archive of Our Own平台。阅读专题下面的文章了解更多详细内容。

382

2026.02.27

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号