java解析xml

参考资料

水平有限,欢迎交流
千问ai
阿伟的反射知识学习
泛型知识学习
软件设计模式(java 版)程细柱

目标 xml

<?xml version="1.0" encoding="UTF-8" ?>  
<conf> 
    <farm>SGFarm</farm>
    <student>        
        <name>李四</name>  
        <age>23</age>  
        <sex>男</sex>  
        <address>北京</address>  
    </student>    
    <teacher>        
        <id>0001</id>  
        <teacherName>王老师</teacherName>  
        <subject>数学</subject>  
        <salary>5000</salary>  
    </teacher>    
    <grades>        
        <grade>            
            <id>001</id>  
            <studentName>李四</studentName>  
            <subject>数学</subject>  
            <score>90</score>  
        </grade>        
        <grade>            
            <id>002</id>  
            <studentName>王五</studentName>  
            <subject>数学</subject>  
            <score>80</score>  
        </grade>    
    </grades>
</conf>

解析简单字符串方法

/**  
 * 从XML文件中读取单一标签的内容,并返回字符串。  
 *  
 * @param xmlPath XML文件的路径。  
 * @param tagName 要查询的XML标签名称。  
 * @return 返回标签内的文本内容。  
 */  
public static String readStringTag(String xmlPath, String tagName) {  
    try {  
        // 初始化DOM解析器工厂  
        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
        DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
        // 解析XML文件  
        Document document = documentBuilder.parse(new File(xmlPath));  
  
        // 查找指定的标签  
        NodeList nodeList = document.getElementsByTagName(tagName);  
        if (nodeList.getLength() == 0) {  
            throw new IllegalArgumentException("No '" + tagName + "' element found in XML file.");  
        }  
  
        // 获取第一个匹配的节点  
        Node node = nodeList.item(0);  
  
        // 检查节点类型是否为元素节点  
        if (node.getNodeType() == Node.ELEMENT_NODE) {  
            Element element = (Element) node;  
            if (element.hasChildNodes()) {  
                Node childNode = element.getFirstChild();  
                if (childNode != null && childNode.getNodeType() == Node.TEXT_NODE) {  
                    return childNode.getNodeValue();  
                }  
            }  
        }  
  
        throw new IllegalArgumentException("The '" + tagName + "' tag does not contain any text.");  
  
    } catch (Exception e) {  
        e.printStackTrace();  
        throw new RuntimeException("Failed to parse XML and retrieve string content", e);  
    }  
}
public static void main(String[] args) {  
    String xmlPath = "src/code/readXml/test.xml";  
    String tagName1 = "student";  
    String tagName2 = "teacher";  
    String tagName3 = "grade";  
    String tagName4 = "farm";  
  
    System.out.println("解析字符串----------------------------------------");  
    String farmContent = ReadXML.readStringTag(xmlPath, tagName4);  
    System.out.println("Farm content: " + farmContent);
}

解析对象

解析单一对象

对象学生定义类

class Student {  
    private String name;  
    private int age;  
    private String sex;  
    private String address;  
  
    @Override  
    public String toString() {  
        return "Student{" +  
                "name='" + name + '\'' +  
                ", age=" + age +  
                ", sex='" + sex + '\'' +  
                ", address='" + address + '\'' +  
                '}';  
    }  
}

对象老师定义类

class Teacher {  
    private int id;  
    private String name;  
    private String subject;  
    private double salary;  
  
    @Override  
    public String toString() {  
        return "Teacher{" +  
                "name='" + name + '\'' +  
                ", id=" + id +  
                ", subject='" + subject + '\'' +  
                ", salary='" + salary + '\'' +  
                '}';  
    }  
}

解析方法

/**  
 * 从XML文件中读取对象信息,并返回指定类型的对象实例。  
 *  
 * @param xmlPath XML文件的路径。  
 * @param tagName 要查询的XML标签名称。  
 * @param clazz   目标类型的Class对象,用于类型安全的返回。  
 * @param mapping 属性名到XML标签的映射。  
 * @param <T>     泛型类型。  
 * @return 返回创建的对象实例。  
 */  
public static <T> T readObjXml(String xmlPath, String tagName, Class<T> clazz, Map<String, String> mapping) {  
    try {  
        // 初始化DOM解析器工厂  
        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
        DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
        // 解析XML文件  
        Document document = documentBuilder.parse(new File(xmlPath));  
  
        // 查找指定标签名的节点列表  
        NodeList nodeList = document.getElementsByTagName(tagName);  
        if (nodeList.getLength() == 0) {  
            throw new IllegalArgumentException("No '" + tagName + "' element found in XML file.");  
        }  
  
        // 获取第一个匹配节点  
        Element element = (Element) nodeList.item(0);  
  
        // 使用反射创建对象实例  
        T instance = clazz.getDeclaredConstructor().newInstance();  
  
        // 设置对象属性  
        for (Map.Entry<String, String> entry : mapping.entrySet()) {  
            String propertyName = entry.getKey();  
            String xmlTagName = entry.getValue();  
  
            Node node = element.getElementsByTagName(xmlTagName).item(0);  
            if (node != null && node.getFirstChild() != null) {  
                String value = node.getFirstChild().getNodeValue();  
                // 设置属性值  
                Field field = clazz.getDeclaredField(propertyName);  
                field.setAccessible(true); // 允许访问私有字段  
                if (field.getType() == Integer.class || field.getType() == int.class) {  
                    field.setInt(instance, Integer.parseInt(value));  
                } else if (field.getType() == Long.class || field.getType() == long.class) {  
                    field.setLong(instance, Long.parseLong(value));  
                } else if (field.getType() == Double.class || field.getType() == double.class) {  
                    field.setDouble(instance, Double.parseDouble(value));  
                } else if (field.getType() == String.class) {  
                    field.set(instance, value);  
                }  
                else {  
                    throw new IllegalArgumentException("Unsupported type for property: " + propertyName);  
                }  
            }  
        }  
  
        return instance;  
    } catch (Exception e) {  
        e.printStackTrace();  
        throw new RuntimeException("Failed to parse XML and create object", e);  
    }  
}
public static void main(String[] args) {  
    String xmlPath = "src/code/readXml/test.xml";  
    String tagName1 = "student";  
    String tagName2 = "teacher";  
    String tagName3 = "grade";   
  
    System.out.println("解析单一对象学生----------------------------------------");  
    Map<String, String> stuMap = new HashMap<>();  
    stuMap.put("name", "name");  
    stuMap.put("age", "age");  
    stuMap.put("sex", "sex");  
    stuMap.put("address", "address");  
    Student students = ReadXML.readObjXml(xmlPath, tagName1, Student.class, stuMap);  
    System.out.println(students);  
  
    System.out.println("解析单一对象老师----------------------------------------");  
    Map<String, String> teaMap = new HashMap<>();  
    teaMap.put("id", "id");  
    teaMap.put("name", "teacherName");  
    teaMap.put("subject", "subject");  
    teaMap.put("salary", "salary");  
    Teacher teachers = ReadXML.readObjXml(xmlPath, tagName2, Teacher.class, teaMap);  
    System.out.println(teachers);
}

解析对象数组

对象成绩定义类

class Grade {  
    private long id;  
    private String stuName;  
    private String subject;  
    private double score;  
  
    @Override  
    public String toString() {  
        return "Grade{" +  
                "id='" + id + '\'' +  
                ", studentName='" + stuName + '\'' +  
                ", subject='" + subject + '\'' +  
                ", score=" + score +  
                '}';  
    }  
}

解析方法

/**  
 * 从XML文件中读取对象信息,并返回指定类型的对象列表。  
 *  
 * @param xmlPath XML文件的路径。  
 * @param tagName 要查询的XML标签名称。  
 * @param clazz   目标类型的Class对象,用于类型安全的返回。  
 * @param mapping 属性名到XML标签的映射。  
 * @param <T>     泛型类型。  
 * @return 返回创建的对象实例列表。  
 */  
public static <T> List<T> readObjsXml(String xmlPath, String tagName, Class<T> clazz, Map<String, String> mapping) {  
    try {  
        // 初始化DOM解析器工厂  
        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
        DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
        // 解析XML文件  
        Document document = documentBuilder.parse(new File(xmlPath));  
  
        // 查找所有的顶层标签  
        NodeList topLevelNodes = document.getChildNodes();  
  
        // 创建对象列表  
        List<T> objects = new ArrayList<>();  
  
        // 遍历所有的顶层标签  
        for (int i = 0; i < topLevelNodes.getLength(); i++) {  
            Node topLevelNode = topLevelNodes.item(i);  
            if (topLevelNode.getNodeType() == Node.ELEMENT_NODE) {  
                Element topLevelElement = (Element) topLevelNode;  
  
                // 查找内部的 tagName 标签节点列表  
                NodeList internalNodes = topLevelElement.getElementsByTagName(tagName);  
  
                // 遍历所有匹配的节点  
                for (int j = 0; j < internalNodes.getLength(); j++) {  
                    Element element = (Element) internalNodes.item(j);  
  
                    // 使用反射创建对象实例  
                    T instance = clazz.getDeclaredConstructor().newInstance();  
  
                    // 设置对象属性  
                    for (Map.Entry<String, String> entry : mapping.entrySet()) {  
                        String propertyName = entry.getKey();  
                        String xmlTagName = entry.getValue();  
  
                        Node node = element.getElementsByTagName(xmlTagName).item(0);  
                        if (node != null && node.getFirstChild() != null) {  
                            String value = node.getFirstChild().getNodeValue();  
                            // 设置属性值  
                            Field field = clazz.getDeclaredField(propertyName);  
                            field.setAccessible(true); // 允许访问私有字段  
                            if (field.getType() == Integer.class || field.getType() == int.class) {  
                                field.setInt(instance, Integer.parseInt(value));  
                            } else if (field.getType() == Long.class || field.getType() == long.class) {  
                                field.setLong(instance, Long.parseLong(value));  
                            } else if (field.getType() == Double.class || field.getType() == double.class) {  
                                field.setDouble(instance, Double.parseDouble(value));  
                            } else if (field.getType() == String.class) {  
                                field.set(instance, value);  
                            } else {  
                                throw new IllegalArgumentException("Unsupported type for property: " + propertyName);  
                            }  
                        }  
                    }  
  
                    objects.add(instance);  
                }  
            }  
        }  
  
        return objects;  
    } catch (Exception e) {  
        e.printStackTrace();  
        throw new RuntimeException("Failed to parse XML and create objects", e);  
    }  
}
public static void main(String[] args) {  
    String xmlPath = "src/code/readXml/test.xml";  
    String tagName1 = "student";  
    String tagName2 = "teacher";  
    String tagName3 = "grade";  
    String tagName4 = "farm";  
    System.out.println("解析对象数组成绩----------------------------------------");  
    Map<String, String> mapping = new HashMap<>();  
    mapping.put("id", "id");  
    mapping.put("stuName", "studentName");  
    mapping.put("subject", "subject");  
    mapping.put("score", "score");  
    List<Grade> grades = ReadXML.readObjsXml(xmlPath, tagName3, Grade.class, mapping);  
    for (Grade grade : grades) {  
        System.out.println(grade);  
    }  
}

完整代码

package code.readXml;  
  
import org.w3c.dom.*;  
import javax.xml.parsers.DocumentBuilder;  
import javax.xml.parsers.DocumentBuilderFactory;  
import java.io.File;  
import java.lang.reflect.Field;  
import java.util.ArrayList;  
import java.util.List;  
import java.util.Map;  
import java.util.HashMap;  
  
class Grade {  
    private long id;  
    private String stuName;  
    private String subject;  
    private double score;  
  
    @Override  
    public String toString() {  
        return "Grade{" +  
                "id='" + id + '\'' +  
                ", studentName='" + stuName + '\'' +  
                ", subject='" + subject + '\'' +  
                ", score=" + score +  
                '}';  
    }  
}  
  
class Teacher {  
    private int id;  
    private String name;  
    private String subject;  
    private double salary;  
  
    @Override  
    public String toString() {  
        return "Teacher{" +  
                "name='" + name + '\'' +  
                ", id=" + id +  
                ", subject='" + subject + '\'' +  
                ", salary='" + salary + '\'' +  
                '}';  
    }  
}  
  
class Student {  
    private String name;  
    private int age;  
    private String sex;  
    private String address;  
  
    @Override  
    public String toString() {  
        return "Student{" +  
                "name='" + name + '\'' +  
                ", age=" + age +  
                ", sex='" + sex + '\'' +  
                ", address='" + address + '\'' +  
                '}';  
    }  
}  
  
public class ReadXML {  
    /**  
     * 从XML文件中读取单一标签的内容,并返回字符串。  
     *  
     * @param xmlPath XML文件的路径。  
     * @param tagName 要查询的XML标签名称。  
     * @return 返回标签内的文本内容。  
     */  
    public static String readStringTag(String xmlPath, String tagName) {  
        try {  
            // 初始化DOM解析器工厂  
            DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
            DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
            // 解析XML文件  
            Document document = documentBuilder.parse(new File(xmlPath));  
  
            // 查找指定的标签  
            NodeList nodeList = document.getElementsByTagName(tagName);  
            if (nodeList.getLength() == 0) {  
                throw new IllegalArgumentException("No '" + tagName + "' element found in XML file.");  
            }  
  
            // 获取第一个匹配的节点  
            Node node = nodeList.item(0);  
  
            // 检查节点类型是否为元素节点  
            if (node.getNodeType() == Node.ELEMENT_NODE) {  
                Element element = (Element) node;  
                if (element.hasChildNodes()) {  
                    Node childNode = element.getFirstChild();  
                    if (childNode != null && childNode.getNodeType() == Node.TEXT_NODE) {  
                        return childNode.getNodeValue();  
                    }  
                }  
            }  
  
            throw new IllegalArgumentException("The '" + tagName + "' tag does not contain any text.");  
  
        } catch (Exception e) {  
            e.printStackTrace();  
            throw new RuntimeException("Failed to parse XML and retrieve string content", e);  
        }  
    }  
    /**  
     * 从XML文件中读取对象信息,并返回指定类型的对象实例。  
     *  
     * @param xmlPath XML文件的路径。  
     * @param tagName 要查询的XML标签名称。  
     * @param clazz   目标类型的Class对象,用于类型安全的返回。  
     * @param mapping 属性名到XML标签的映射。  
     * @param <T>     泛型类型。  
     * @return 返回创建的对象实例。  
     */  
    public static <T> T readObjXml(String xmlPath, String tagName, Class<T> clazz, Map<String, String> mapping) {  
        try {  
            // 初始化DOM解析器工厂  
            DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
            DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
            // 解析XML文件  
            Document document = documentBuilder.parse(new File(xmlPath));  
  
            // 查找指定标签名的节点列表  
            NodeList nodeList = document.getElementsByTagName(tagName);  
            if (nodeList.getLength() == 0) {  
                throw new IllegalArgumentException("No '" + tagName + "' element found in XML file.");  
            }  
  
            // 获取第一个匹配节点  
            Element element = (Element) nodeList.item(0);  
  
            // 使用反射创建对象实例  
            T instance = clazz.getDeclaredConstructor().newInstance();  
  
            // 设置对象属性  
            for (Map.Entry<String, String> entry : mapping.entrySet()) {  
                String propertyName = entry.getKey();  
                String xmlTagName = entry.getValue();  
  
                Node node = element.getElementsByTagName(xmlTagName).item(0);  
                if (node != null && node.getFirstChild() != null) {  
                    String value = node.getFirstChild().getNodeValue();  
                    // 设置属性值  
                    Field field = clazz.getDeclaredField(propertyName);  
                    field.setAccessible(true); // 允许访问私有字段  
                    if (field.getType() == Integer.class || field.getType() == int.class) {  
                        field.setInt(instance, Integer.parseInt(value));  
                    } else if (field.getType() == Long.class || field.getType() == long.class) {  
                        field.setLong(instance, Long.parseLong(value));  
                    } else if (field.getType() == Double.class || field.getType() == double.class) {  
                        field.setDouble(instance, Double.parseDouble(value));  
                    } else if (field.getType() == String.class) {  
                        field.set(instance, value);  
                    }  
                    else {  
                        throw new IllegalArgumentException("Unsupported type for property: " + propertyName);  
                    }  
                }  
            }  
  
            return instance;  
        } catch (Exception e) {  
            e.printStackTrace();  
            throw new RuntimeException("Failed to parse XML and create object", e);  
        }  
    }  
    /**  
     * 从XML文件中读取对象信息,并返回指定类型的对象列表。  
     *  
     * @param xmlPath XML文件的路径。  
     * @param tagName 要查询的XML标签名称。  
     * @param clazz   目标类型的Class对象,用于类型安全的返回。  
     * @param mapping 属性名到XML标签的映射。  
     * @param <T>     泛型类型。  
     * @return 返回创建的对象实例列表。  
     */  
    public static <T> List<T> readObjsXml(String xmlPath, String tagName, Class<T> clazz, Map<String, String> mapping) {  
        try {  
            // 初始化DOM解析器工厂  
            DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();  
            DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();  
  
            // 解析XML文件  
            Document document = documentBuilder.parse(new File(xmlPath));  
  
            // 查找所有的顶层标签  
            NodeList topLevelNodes = document.getChildNodes();  
  
            // 创建对象列表  
            List<T> objects = new ArrayList<>();  
  
            // 遍历所有的顶层标签  
            for (int i = 0; i < topLevelNodes.getLength(); i++) {  
                Node topLevelNode = topLevelNodes.item(i);  
                if (topLevelNode.getNodeType() == Node.ELEMENT_NODE) {  
                    Element topLevelElement = (Element) topLevelNode;  
  
                    // 查找内部的 tagName 标签节点列表  
                    NodeList internalNodes = topLevelElement.getElementsByTagName(tagName);  
  
                    // 遍历所有匹配的节点  
                    for (int j = 0; j < internalNodes.getLength(); j++) {  
                        Element element = (Element) internalNodes.item(j);  
  
                        // 使用反射创建对象实例  
                        T instance = clazz.getDeclaredConstructor().newInstance();  
  
                        // 设置对象属性  
                        for (Map.Entry<String, String> entry : mapping.entrySet()) {  
                            String propertyName = entry.getKey();  
                            String xmlTagName = entry.getValue();  
  
                            Node node = element.getElementsByTagName(xmlTagName).item(0);  
                            if (node != null && node.getFirstChild() != null) {  
                                String value = node.getFirstChild().getNodeValue();  
                                // 设置属性值  
                                Field field = clazz.getDeclaredField(propertyName);  
                                field.setAccessible(true); // 允许访问私有字段  
                                if (field.getType() == Integer.class || field.getType() == int.class) {  
                                    field.setInt(instance, Integer.parseInt(value));  
                                } else if (field.getType() == Long.class || field.getType() == long.class) {  
                                    field.setLong(instance, Long.parseLong(value));  
                                } else if (field.getType() == Double.class || field.getType() == double.class) {  
                                    field.setDouble(instance, Double.parseDouble(value));  
                                } else if (field.getType() == String.class) {  
                                    field.set(instance, value);  
                                } else {  
                                    throw new IllegalArgumentException("Unsupported type for property: " + propertyName);  
                                }  
                            }  
                        }  
  
                        objects.add(instance);  
                    }  
                }  
            }  
  
            return objects;  
        } catch (Exception e) {  
            e.printStackTrace();  
            throw new RuntimeException("Failed to parse XML and create objects", e);  
        }  
    }  
  
    public static void main(String[] args) {  
        String xmlPath = "src/code/readXml/test.xml";  
        String tagName1 = "student";  
        String tagName2 = "teacher";  
        String tagName3 = "grade";  
        String tagName4 = "farm";  
  
        System.out.println("解析字符串----------------------------------------");  
        String farmContent = ReadXML.readStringTag(xmlPath, tagName4);  
        System.out.println("Farm content: " + farmContent);  
  
        System.out.println("解析单一对象学生----------------------------------------");  
        Map<String, String> stuMap = new HashMap<>();  
        stuMap.put("name", "name");  
        stuMap.put("age", "age");  
        stuMap.put("sex", "sex");  
        stuMap.put("address", "address");  
        Student students = ReadXML.readObjXml(xmlPath, tagName1, Student.class, stuMap);  
        System.out.println(students);  
  
        System.out.println("解析单一对象老师----------------------------------------");  
        Map<String, String> teaMap = new HashMap<>();  
        teaMap.put("id", "id");  
        teaMap.put("name", "teacherName");  
        teaMap.put("subject", "subject");  
        teaMap.put("salary", "salary");  
        Teacher teachers = ReadXML.readObjXml(xmlPath, tagName2, Teacher.class, teaMap);  
        System.out.println(teachers);  
  
        System.out.println("解析对象数组成绩----------------------------------------");  
        Map<String, String> mapping = new HashMap<>();  
        mapping.put("id", "id");  
        mapping.put("stuName", "studentName");  
        mapping.put("subject", "subject");  
        mapping.put("score", "score");  
        List<Grade> grades = ReadXML.readObjsXml(xmlPath, tagName3, Grade.class, mapping);  
        for (Grade grade : grades) {  
            System.out.println(grade);  
        }  
    }  
}
posted @ 2024-09-24 17:50  yuanyulinyi  阅读(7)  评论(0编辑  收藏  举报