2021-02-25

生成和解析XML

  1. 什么是XML,XML的作用是什么,如何编写XML文件?

XML就是可扩展标记语言HTML相似都是标记语言

XML提供的标记都是自定义的;HTML提供的标记都是预先定义好的。

XML用来存储数据的文本格式;HTML是同来设计网页。

XML是一种简单的数据存储语言

如何编写XML文件?

一个简单的XML文件格式

<?xml version="1.0"  encoding=”utf-8”?>

<students>

<student  id=”1001” >

     <name>zhangsan</name>

     <age>23</age>

     <sex>男</sex>

</student>

<student  id=”1002”>

     <name>lisi</name>

     <age>24</age>

     <sex>女</sex>

</student>

</students>

说明:

<?xml version="1.0"  encoding=utf-8?>---xml的文件头,表示xml文档开始。与html中的“<!DOCTYPE html>”作用相似。【土地】

<students></students>----自定义的xml标记,表示一个xml文件的根元素。【树根】

<student  id=1001 ></student>---自定义的xml标记,表示一个xml文件的根元素中的子元素。【树枝】

id=1001, id=1002----元素的属性,是一个键值对。

<name></name>,<age></age>,<sex></sex>---自定义的xml标记,表示一个xml文件的根元素中的子子元素。【树叶】

zhangsan,23,男...---都是被存储的具体数据值。【果实】

注意:1.标记都是自定义的,成对出现“<name></name>”

           2.元素可以携带属性,属性是一个键值对,可以出现多个

         例如:<小狗 id=1001 color=黑色></小狗>

          3.保存文件的时候,文件的后缀名是以“.xml”结尾

例如:

public class Person{

    private int  perid;

    private String  pername;

    private int perage;

    private String peraddress;

     ......

    getXXXX()/setXXXX();

}

Person  person1=new Person();

person1.setPerid(1001);

person1.setPername(“张三”);

person1.setPernage(23);

person1.setPernaddress(“西安”);

Person  person2=new Person();

person2.setPerid(1002);

person2.setPername(“李四”);

person2.setPernage(24);

person2.setPernaddress(“北京”);

List<Person>  personlist=new ArrayList<Person>();

personlist.add(person1);

personlist.add(person2);

请将上面的personlist集合转换成xml文件?

<?xml version="1.0"  encoding=”utf-8”?>

<personlist>

    <person perid=”1001” >

        <pername>张三</pername>

        <perage>23</perage>

        <peraddress>西安</peraddress>

    </person>

    <person perid=”1002” >

        <pername>李四</pername>

        <perage>24</perage>

        <peraddress>北京</peraddress>

    </person>

</personlist>
  1. 常见的XML文件的生成方式和解析方式

2.1 XML文件的生成【Dom生成

1.java默认的dom生成方式

public static void creatXMLByJavaDom(List<Person> personlist)throws Exception {

    //得到DOM解析器工厂

    DocumentBuilderFactory  builderFactory=DocumentBuilderFactory.newInstance();

    //从解析器工厂的解析器

    DocumentBuilder documentBuilder=builderFactory.newDocumentBuilder();

    //得到Document对象

    Document document=documentBuilder.newDocument();

    //设置文件头

    document.setXmlStandalone(true);

    //得到根元素

    Element rootElement=document.createElement("personlist");

    //循环遍历集合,创建子元素,将子元素添加到根元素

        for(Person person:personlist) {

        //创建子元素

        Element personElement=document.createElement("person");

        //为子元素添加属性

        personElement.setAttribute("perid", String.valueOf(person.getPerid()));

        //创建子子元素

        Element nameElement=document.createElement("pername");

        Element ageElement=document.createElement("perage");

        Element addressElement=document.createElement("peraddress");

        //为子子元素添加数据值

        nameElement.setTextContent(person.getPername());

        ageElement.setTextContent(String.valueOf(person.getPerage()));

        addressElement.setTextContent(person.getPeraddress());

        //将子子元素添加到子元素

        personElement.appendChild(nameElement);

        personElement.appendChild(ageElement);

        personElement.appendChild(addressElement);

        //将子元素添加到根元素

        rootElement.appendChild(personElement);

    }

    //将根元素添加到Document对象中

    document.appendChild(rootElement);

    // 创建TransformerFactory对象

    TransformerFactory tff = TransformerFactory.newInstance();

    // 创建 Transformer对象

    Transformer tf = tff.newTransformer();

    // 输出内容是否使用换行

    tf.setOutputProperty(OutputKeys.INDENT, "yes");

    // 创建xml文件并写入内容

    tf.transform(new DOMSource(document), new StreamResult(new File("person1.xml")));

}

2.使用第三方开发包

  A.dom4j

/**

* 使用第三方开发包Dom4j生成xml

*  下载导入Dom4j的开发包

* @param personlist

*/

public static void creatXMLByDom4j(List<Person> personlist)throws Exception {

    //得到Document对象

    Document document=DocumentHelper.createDocument();

    //创建根元素

    Element rootElement=document.addElement("personlist");

    //循环遍历集合,创建子元素,将子元素添加到根元素

    for(Person  person:personlist) {

        //创建子元素

        Element personElement=rootElement.addElement("person");

        //添加属性

        personElement.addAttribute("perid", String.valueOf(person.getPerid()));

        //创建子子元素

        Element nameElement=personElement.addElement("pername");

        Element ageElement=personElement.addElement("perage");

        Element addressElement=personElement.addElement("peraddress");

        //为子子元素设置数据值

        nameElement.setText(person.getPername());

        ageElement.setText(String.valueOf(person.getPerage()));

        addressElement.setText(person.getPeraddress());

    }

    //设置生成xml的格式

    OutputFormat format = OutputFormat.createPrettyPrint();

    // 设置编码格式

    format.setEncoding("UTF-8");

    //创建XML字符输出流

    XMLWriter writer = new XMLWriter(new FileOutputStream(new File("person2.xml")), format);

    //设置是否转义,默认使用转义字符

    writer.setEscapeText(false);

    //写出Document对象

    writer.write(document);

    //关闭流

    writer.close();

}

  B.jdom 

/**

* 使用第三方开发包jdom生成xml

*下载导入jdom的开发包

* @param personlist

*/

public static void creatXMLByJdom(List<Person> personlist)throws Exception {

    //创建根元素

    Element rootElement=new Element("personlist");

    //循环遍历集合,创建子元素,将子元素添加到根元素

    for(Person  person:personlist) {

        //创建子元素

        Element personElement=new Element("person");

        //设置属性

        personElement.setAttribute("perid", String.valueOf(person.getPerid()));

        //创建子子元素

        Element nameElement=new Element("pername");

        Element ageElement=new Element("perage");

        Element addressElement=new Element("peraddress");

        //为子子元素设置数据值

        nameElement.setText(person.getPername());

        ageElement.setText(String.valueOf(person.getPerage()));

        addressElement.setText(person.getPeraddress());

        //将子子元素添加到子元素

        personElement.addContent(nameElement);

        personElement.addContent(ageElement);

        personElement.addContent(addressElement);

        //将子元素添加到根元素

        rootElement.addContent(personElement);

    }

    //依赖根元素创建Document

    Document document=new Document(rootElement);

    //输出Document对象

    Format format = Format.getCompactFormat();

    // 设置换行Tab或空格

    format.setIndent("  ");

    format.setEncoding("UTF-8");

    // 创建XMLOutputter的对象

    XMLOutputter outputer = new XMLOutputter(format);

    //写出Document

    outputer.output(document, new FileOutputStream(new File("person3.xml")));

}
 /**

 * 通过拼接字符串的方式创建一个xml文件

 * @param personlist

 * @throws Exception

 */

public  static void createXML4(List<Person>  personlist)throws Exception{

    //定义一个保存拼接好的字符串变量

    String  xmlcontent=null;

    //为了拼接字符串更加方便我们使用stringbuilder类拼接字符串

    StringBuilder  stringBuilder=new StringBuilder();

    stringBuilder.append("<?xml version=\"1.0\" encoding=\"UTF-8\"?>");

    stringBuilder.append("\r\n");

    stringBuilder.append("<personlist>");

    stringBuilder.append("\r\n");

    //遍历需要被生成成xml文件的集合

    for(Person  person:personlist){

        stringBuilder.append("\t<person  perid=\""+person.getPerid()+"\">");

        stringBuilder.append("\r\n");

        stringBuilder.append("\t\t<pername>"+person.getPername()+"</pername>");

        stringBuilder.append("\r\n");

        stringBuilder.append("\t\t<perage>"+person.getPerage()+"</perage>");

        stringBuilder.append("\r\n");

        stringBuilder.append("\t\t<peraddress>"+person.getPeraddress()+"</peraddress>");

        stringBuilder.append("\r\n");

        stringBuilder.append("\t</person>");

        stringBuilder.append("\r\n");

    }

    stringBuilder.append("<personlist>");

    xmlcontent=stringBuilder.toString();

    System.out.println(xmlcontent);

    //创建输出流对象,将创建好的xml,保存到文件中

    File file=new File("F:"+File.separator+"personlist.xml");

    BufferedWriter  out=new BufferedWriter(new FileWriter(file));

    out.write(xmlcontent);

    out.close();

}

2.2 XML文件的解析

       实际上就是将xml文件中保存的数据取出,转换成java对象

  1. DOM(Document Object Model)解析

            Java默认的Dom  /  dom4j  /  jdom

将整个xml文件读取成一个Document对象,然后从Document对象中得到根元素,再从根元素中得到子元素,接着从子元素中得到子子元素,最后从子子元素中得到数据值。

/**

* Java默认的Dom解析xml

*/

public static List<Person> parseXMLByDom()throws Exception {

    //定义保存对象的集合

    List<Person> personlist=new ArrayList<Person>();

    //得到解析器工厂发

    DocumentBuilderFactory builderFactory=DocumentBuilderFactory.newInstance();

    //得到解析器对象

    DocumentBuilder documentBuilder=builderFactory.newDocumentBuilder();

    //将需要被解析的xml文件读取成Document对象

    Document document=documentBuilder.parse(new File("person3.xml"));

    //从Document对象中取出一组子元素

    NodeList personNodeList =document.getElementsByTagName("person");

    for(int i=0;i<personNodeList.getLength();i++) {

        //创建Person对象用来保存解析出的数据值

        Person  person=new Person();

        //得到子元素

        Node  personNode=personNodeList.item(i);

        //得到默认的属性值

        String perid=personNode.getAttributes().item(0).getNodeValue();

        person.setPerid(Integer.parseInt(perid));

        //从子元素中得到包含有子子元素的一组集合

        NodeList nodeList=personNode.getChildNodes();

        for(int j=0;j<nodeList.getLength();j++) {

            //得到子子元素

            Node  node=nodeList.item(j);

            //得到子子元素的文本值

            if(node.getNodeName().equals("pername")) {

                String pername=node.getTextContent();

                person.setPername(pername);

            }

            if(node.getNodeName().equals("perage")) {

            String perage=node.getTextContent();

            person.setPerage(Integer.parseInt(perage));

            }

            if(node.getNodeName().equals("peraddress")) {

            String peraddress=node.getTextContent();

            person.setPeraddress(peraddress);

            }

        }

        //将解析好的person对象装入集合

        personlist.add(person);

    }

    return personlist;

}
/**

 * 使用dom4j解析xml

 * @return

 */

public static List<Person> parseXMLByDom4j()throws Exception {

    //定义保存对象的集合

    List<Person> personlist=new ArrayList<Person>();

    //创建xml解析器对象

    SAXReader   saxReader=new SAXReader();

    //通过解析器对象读取被解析的xml文件一个Document

    Document  document=saxReader.read(new File("person3.xml"));

    //得到根元素

    Element  rootElement=document.getRootElement();

    //从根元素中得到一组person的子元素

    List<Element> elementlist=rootElement.elements("person");

    for(Element perElement:elementlist) {

        //创建Person对象用来保存解析出的数据值

        Person  person=new Person();

        //根据属性名称得到属性值

        String perid=perElement.attributeValue("perid");

        //得到子子元素

        Element nameElement=perElement.element("pername");

        Element ageElement=perElement.element("perage");

        Element addressElement=perElement.element("peraddress");

        //得到子子元素的数据值

        String pername=nameElement.getText();

        String perage=ageElement.getText();

        String peraddress=addressElement.getText();

        //封装Perosn对象

        person.setPerid(Integer.parseInt(perid));

        person.setPername(pername);

        person.setPerage(Integer.parseInt(perage));

        person.setPeraddress(peraddress);

        //将封装Perosn对象装入集合

        personlist.add(person);

   }

   return personlist;

}
/**

* 使用jdom解析xml

* @return

*/

public static List<Person> parseXMLByjdom()throws Exception {

    //定义保存对象的集合

    List<Person> personlist=new ArrayList<Person>();

    //得到解析器对象

    SAXBuilder saxBuilder=new SAXBuilder();

    //读取被解析的xml文件成document

    Document  document=saxBuilder.build(new File("person3.xml"));

    //得到根元素

    Element  rootElement= document.getRootElement();

    //从根元素中得到一组person的子元素

    List<Element>  elementList=rootElement.getChildren("person");

    for(Element perElement:elementList) {

        /*

        //创建Person对象用来保存解析出的数据值

        Person  person=new Person();

        //得到属性值

        String perid=perElement.getAttributeValue("perid");

        //得到子子元素

        Element nameElement=perElement.getChild("pername");

        Element ageElement=perElement.getChild("perage");

        Element addressElement=perElement.getChild("peraddress");

        //得到子子元素的数值

        String pername=nameElement.getText();

        String perage=ageElement.getText();

        String peraddress=addressElement.getText();

        //封装Perosn对象

        person.setPerid(Integer.parseInt(perid));

        person.setPername(pername);

        person.setPerage(Integer.parseInt(perage));

        person.setPeraddress(peraddress);

        //将封装Perosn对象装入集合

        personlist.add(person);

        */

        //创建Person对象用来保存解析出的数据值

        Person  person=new Person();

        person.setPerid(Integer.parseInt(perElement.getAttributeValue("perid")));

        person.setPername(perElement.getChildText("pername"));

        person.setPerage(Integer.parseInt(perElement.getChildTextTrim("perage")));

        person.setPeraddress(perElement.getChildText("peraddress"));

        //将封装Perosn对象装入集合

        personlist.add(person);

        }

    return personlist;

    }

}

DOM(Document Object Model)解析的原理就是需要被解析的xml文件,读取成一个文档树【Document 对象】,依据提供的开发类库和方法从文档树中得到根元素,再从根元素中得到子元素,从子元素中的到子子元素,再得到具体的数据值。

优点:结构清晰明了。

缺点:通常需要加载整个XML文档来构造层次结构,消耗资源大.

  1. SAX(Simple API for XML)解析
package com.wangxing.util;

import java.util.ArrayList;

import java.util.List;

import org.xml.sax.Attributes;

import org.xml.sax.SAXException;

import org.xml.sax.helpers.DefaultHandler;

import com.wangxing.bean.Person;

public class MyDefaultHandler extends DefaultHandler{

    private  List<Person>  personList=null;

    private  Person  person=null;

    private  String elementName="";

    public  List<Person> getPersonList(){

        return personList;

    }

    /**

    * 文档开始的解析方法

    */

    @Override

    public void startDocument() throws SAXException {

        personList=new ArrayList<Person>();

    }

    /**

    * 元素开始的解析方法

    */

    @Override

    public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {

        if(qName.equals("person")) {

            person=new Person();

            //得到perid的属性值

            String perid=attributes.getValue("perid");

            person.setPerid(Integer.parseInt(perid));

        }

        if(qName.equals("pername")) {

            elementName=qName;

        }

        if(qName.equals("perage")) {

            elementName=qName;

        }

        if(qName.equals("peraddress")) {

            elementName=qName;

        }

    }

    /**

     * 读取文本值数据

     */

    @Override

    public void characters(char[] ch, int start, int length) throws SAXException {

        String  value=new String(ch,start,length);

        if(elementName.equals("pername")) {

            person.setPername(value);

        }

        if(elementName.equals("perage")) {

            person.setPerage(Integer.parseInt(value));

        }

        if(elementName.equals("peraddress")) {

            person.setPeraddress(value);

        }

    }

    /**

    * 元素结束的解析方法

    */

    @Override

    public void endElement(String uri, String localName, String qName) throws SAXException {

        if(qName.equals("person")) {

            personList.add(person);

            person=null;

            elementName="";

        }else{

            elementName="";

        }

    }

    /**

     * 文档结束的解析方法

     */

    @Override

    public void endDocument() throws SAXException {

    }

}

    /**

     * 使用sax解析xml

     * @return

     */

    public static List<Person> parseXMLBySax()throws Exception {

        //定义保存对象的集合

        List<Person> personlist=new ArrayList<Person>();

        //得到SAX解析器工厂

        SAXParserFactory saxfac = SAXParserFactory.newInstance();

        //从工厂中得到解析器对象

        SAXParser   saxParser=saxfac.newSAXParser();

        //解析方法的参数

        //参数1--File对象【被解析的xml文件】

        //参数2--DefaultHandler对象【具体的xml解析过程】

        //需要创建一个DefaultHandler类的子类,重写解析过程

        MyDefaultHandler  myDefaultHandler=new MyDefaultHandler();

        saxParser.parse(new File("person3.xml"), myDefaultHandler);

        return myDefaultHandler.getPersonList();

    }

SAX(Simple API for XML)解析xml文件的原理是基于事件的模型,它在解析XML文档的时候可以触发一系列的事件,当发现给定的标签的时候,它可以激活一个回调方法,告诉该方法指定的标签已经找到,如果这个指定的标记中中有我们需要数据值就解析,没有就不用处理。

读取一个元素,判断这一个元素属于xml文件的哪一个元素【文档开始/文档结束/标记开始/标记结束/文本元素】,不同的元素触发不同的方法来执行解析数据,如果当前元素中没有数据值就跳过读取下一个元素。

优点:1.只在读取数据时检查数据,不需要保存在内存中 

        2.可以在某个条件得到满足时停止解析,不必解析整个文档。

        3.效率和性能较高,能解析大于系统内存的文档。

缺点:没有清晰的解析结构

3.XML文件解析方式的区别

DOM(Document Object Model)解析的原理就是需要被解析的xml文件,读取成一个文档树【Document 对象】,依据提供的开发类库和方法从文档树中得到根元素,再从根元素中得到子元素,从子元素中的到子子元素,再得到具体的数据值。

优点:结构清晰明了。

缺点:通常需要加载整个XML文档来构造层次结构,消耗资源大.

SAX(Simple API for XML)解析xml文件的原理是基于事件的模型,它在解析XML文档的时候可以触发一系列的事件,当发现给定的标签的时候,它可以激活一个回调方法,告诉该方法指定的标签已经找到,如果这个指定的标记中中有我们需要数据值就解析,没有就不用处理。

优点:1.只在读取数据时检查数据,不需要保存在内存中 

        2.可以在某个条件得到满足时停止解析,不必解析整个文档。

        3.效率和性能较高,能解析大于系统内存的文档。

缺点:没有清晰的解析结构

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值