我的传智播客之javaweb_day06学习总结

schema约束

  • schema符合xml的语法,xml语句。
  • 一个xml中可以有多个schema,多个schema使用名称空间(类似于java的包)区分。
  • schema里面支持更多的数据类型。
  • schema语法更加复杂,schema目前不能替代dtd。

schema的快速入门

  • schema文件用w3c提供的属性和标签来约束xml文件
  • 创建一个schema文件

    • 根节点<schema>

      • <schema>的属性

        • xmlns=”http://www.w3.org/2001/XMLSchema”
          表示当前xml文件是一个约束文件
        • targetNamespace=”http://www.itcast.cn/20151111”
          使用schema约束文件时,直接通过这个地址引入约束文件

        • elementFormDefault=”qualified”

    • 步骤
      • 看xml有多少个元素<element>
      • 看简单元素和复杂元素
        • 复杂元素:
        • 简单元素:写在复杂元素内
        • 在被约束文件里面引入约束文件
// 复杂元素:
<element name="元素名">
    <complexType>
        <sequence>
            子元素
        </sequence>
    </complexType>
</element>

// 简单元素:写在复杂元素内
<sequence>
    <element name="name" type="string"></element>
    <element name="age" type="int"></element>
</sequence>

// 在被约束文件里面引入约束文件
<person xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://www.itcast.cn/20151111"     xsi:schemaLocation="http://www.itcast.cn/20151111 1.xsd">

// 表示xml是一个被约束文件
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
// 是约束文档里面的targetNamespace
xmlns="http://www.itcast.cn/20151111"
// targetNamespace 空格 约束文件的路径
xsi:schemaLocation="http://www.itcast.cn/20151111 1.xsd">
  • <sequence>:表示元素出现的顺序
  • <all>:元素只能出现一次
  • <choice>:元素只能出现其中的一个
  • <elment name="xxx" maxOccurs="unbounded">:表示元素出现的次数
  • <any></any>:表示任意元素
  • 可以约束属性:写在复杂元素里面,写在</complexType>之前
// name:属性名称
// type:属性类型
// use:属性是否必须出现
<attribute name="id1" type="int" use="required"></attribute>

sax解析的原理

  • sax方式:事件驱动,边读边解析
  • 在javax.xml.parser包里面
    • SAXParser:此类的实例可以从SAXParserFactory.newSAXParser()方法获取
      • parese(File f, DefaltHandler dh):第一个参数:xml路径;第二个参数:事件处理器
    • SAXParserFactory:实例 newInstance()方法得到
  • Sax执行过程
    • 当解析到开始标签时候,自动执行startElement方法
    • 当解析到文本时候,自动执行characters方法
    • 当解析到结束标签时候,自动执行endElement方法

使用jaxp的sax方式解析xml

sax方式不能实现增删改操作,能能做查询操作。

  • 打印整个文档
  • 执行parse方法,第一个参数是xml路径;第二个参数是时间处理器,创建一个类,继承时间处理器的类,重写里面的三个方法
  • 获取所有name元素的值
    • 定义一个成员变量 falg=false
    • 判断开始方法是否是name元素,如果是name元素,把flag值设置为true
    • 如果flag是true,在characters方法里打印内容
    • 当执行到结束方法时,把flag设置成false
  • 获取第一个name元素的值
    • 定义一个成员变量index = 1
    • 在结束方法中 index++;
    • 打印第一个name的值,在characters方法里判断:flag=true且index=1
package cn.itcast.jaxpsax;

import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

public class TestSax {

    public static void main(String[] args) throws Exception {
        /*
         * 1.创建解析器工厂 
         * 2.创建解析器
         * 3创建一个继承DefaultHandler的类 4.执行parse方法
         */
        SAXParserFactory saxParserFactory = SAXParserFactory.newInstance();
        SAXParser saxParser = saxParserFactory.newSAXParser();
        saxParser.parse("src/p1.xml", new Default1());
        saxParser.parse("src/p1.xml", new Default2());
        saxParser.parse("src/p1.xml", new Default3());
    }

}

class Default1 extends DefaultHandler {
    @Override
    public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
        System.out.print("<" + qName + ">");
    }

    @Override
    public void characters(char[] ch, int start, int length) throws SAXException {
        System.out.print(new String(ch, start, length));
    }

    @Override
    public void endElement(String uri, String localName, String qName) throws SAXException {
        System.out.print("</" + qName + ">");
    }

}

class Default2 extends DefaultHandler {
    private boolean flag = false;
    @Override
    public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
        if ("name".equals(qName)) {
            flag = true;
        }
    }

    @Override
    public void characters(char[] ch, int start, int length) throws SAXException {
        if (flag == true) {
            System.out.println(new String(ch, start, length));
        }
    }

    @Override
    public void endElement(String uri, String localName, String qName) throws SAXException {
        flag = false;
    }

}

class Default3 extends DefaultHandler {
    private boolean flag = false;
    private int index = 1;
    @Override
    public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
        if ("name".equals(qName)) {
            flag = true;
        }
    }

    @Override
    public void characters(char[] ch, int start, int length) throws SAXException {
        if (flag == true && index == 1) {
            System.out.println(new String(ch, start, length));
        }
    }

    @Override
    public void endElement(String uri, String localName, String qName) throws SAXException {
        flag = false;
        if ("name".equals(qName)) {
            index++;
        }
    }

}

使用dom4j解析xml

  • dom4j不是javase的一部分,需要导入dom4j的jar包
  • 得到document
    • SAXReader reader = new SAXReader();
    • Document document = reader.read(url);
  • document的父接口是Node
    • 如果在document里面找不到想要的方法,到Node里面去找
  • document里面的方法 getRootElement():获取根节点 返回Element
  • Element也是一个接口,父接口是Node
    • getParent():获取父节点
    • addElement():添加标签

使用dom4j查询xml

// src/p1.xml
<?xml version="1.0" encoding="UTF-8"?>

<person>
    <p1 id1="AAA">
        <name>zhangsan</name>
        <age>30</age>
    </p1>
    <p1>
        <name>lisi</name>
        <age>30</age>
    </p1>
</person>
  • 查询所有name元素里面的值
    • 创建解析器
    • 得到document
    • 得到根节点 getRootElement()
    • 得到所有的p1标签
      • elements(“p1”) 返回list集合
      • 遍历list得到每一个p1
        • element(qname):获取标签下第一个子标签
        • elements(qname):获取标签下所有子标签(一层)
        • elments():获取标签下所有一层子标签
    • 得到name
      • 在p1下执行element(“name”)
    • 得到name里面的值
      • getText()
// 查询xml里面所有的name值
public static void selectAllName() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点 getRootElement()
     * 4.得到所有的p1标签
     * 5.得到name
     * 6.得到name里面的值
     */
    SAXReader saxReader = new SAXReader();
    Document document = saxReader.read("src/p1.xml");
    Element root = document.getRootElement();
    List<Element> list = root.elements("p1");
    for (Element element : list) {
        Element name = element.element("name");
        String s = name.getText();
        System.out.println(s);
    }
}
  • 查询第一个name元素的值
    • 创建解析器
    • 得到document
    • 得到根节点 getRootElement()
    • 得到第一个p1标签
      • element(“p1”)
    • 得到name
      • element(“name”)
    • 得到name里面的值
      • getText()
// 获取到第一个name元素里面的值
public static void selectSinName() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点 getRootElement()
     * 4.得到第一个p1标签
     * 5.得到name
     * 6.得到name里面的值
     */
    SAXReader saxReader = new SAXReader();
    Document document = saxReader.read("src/p1.xml");
    Element root = document.getRootElement();
    Element p1 = root.element("p1");
    Element name = p1.element("name");
    String s = name.getText();
    System.out.println(s);
}
  • 查询第二个name元素的值
    • 创建解析器
    • 得到document
    • 得到根节点
    • 得到所有的p1标签 返回list集合
    • 得到第二个p 使用下标得到
    • 得到第二个name
    • 得到name的值
// 获取到第二个name元素里面的值
public static void selectSecName() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点 getRootElement()
     * 4.得到所有p1
     * 5.得到第二个p1
     * 6.得到name里面的值
     */
    SAXReader saxReader = new SAXReader();
    Document document = saxReader.read("src/p1.xml");
    Element root = document.getRootElement();
    List<Element> list = root.elements("p1");
    Element p2 = list.get(1);
    Element name = p2.element("name");
    String s = name.getText();
    System.out.println(s);
}

使用dom4j实现添加操作

  • 在第一个p1标签末尾添加一个元素<sex>nv</sex>
    • 创建解析器
    • 得到document
    • 得到根节点
    • 得到第一个p1
    • 在p1下添加元素
    • 在添加完成之后的元素下添加文本
    • 回写xml
      • 格式化类 OutputFormat 使用类方法createPrettyPrint()
      • 使用类XMLWriter,传递两个参数
        • new FileOutputStream(“xml的路径”)
        • 格式化类
// 在第一个p1标签末尾添加一个元素<sex>nv</sex>
public static void addSex() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点 getRootElement()
     * 4.获取第一个p1
     * 5.在p1下添加元素
     * 6.在添加完成之后的元素下添加文本 7.回写xml
     */
    // 创建解析器
    SAXReader saxReader = new SAXReader();
    // 得到document
    Document document = saxReader.read("src/p1.xml");
    // 得到根节点
    Element root = document.getRootElement();
    // 得到第一个p1元素
    Element p1 = root.element("p1");
    // 在p1下添加元素
    Element sex = p1.addElement("sex");
    // 在添加完成之后的元素下添加文本
    sex.setText("nv");
    // 回写xml
    OutputFormat format = OutputFormat.createPrettyPrint();
    XMLWriter xmlWriter = new XMLWriter(new FileOutputStream("src/p1.xml"), format);
    xmlWriter.write(document);
    xmlWriter.close();
}

在特定位置添加元素

  • 在第一个p1下面的age标签之前添加<school>ecit</school>
    • 创建解析器
    • 得到document
    • 得到根节点
    • 得到第一个p1
    • 获取p1下面的所有元素
      • elements()方法,返回list集合
      • 创建元素,在元素下创建文本:DocumentHelper.createElement(“school”);
      • 使用list里的方法,在特定位置添加元素:add(int index, E element)
    • 回写xml
// Dom4jUtils类
package cn.itcast.utils;

import java.io.FileOutputStream;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.SAXReader;
import org.dom4j.io.XMLWriter;

public class Dom4jUtils {
    public static final String PATH = "src/p1.xml";
    // 返回document
    public static Document getDocument(String path) {
        try {// 创建解析器
            SAXReader reader = new SAXReader();
            // 得到document
            Document document = reader.read(path);
            return document;
        } catch (DocumentException e) {
            e.printStackTrace();
        }
        return null;
    }

    // 回写xml
    public static void xmlWriters(String path, Document document) {
        OutputFormat format = OutputFormat.createPrettyPrint();
        XMLWriter xmlWriter;
        try {
            xmlWriter = new XMLWriter(new FileOutputStream(path), format);
            xmlWriter.write(document);
            xmlWriter.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
public static void addSchoolBeforeAge() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点
     * 4.得到第一个p1
     * 5.获取p1下面的所有元素
     *  elements()方法,返回list集合 创建元素,在元素下创建文本
     *  DocumentHelper.createElement("school"); 使用list里的方法,在特定位置添加元素 add(int index, E element)
     * 6.回写xml
     */
    Document document = Dom4jUtils.getDocument("src/p1.xml");
    Element root = document.getRootElement();
    Element p1 = root.element("p1");
    List list = p1.elements();
    Element school = DocumentHelper.createElement("school");
    school.setText("ecit");
    list.add(1, school);
    Dom4jUtils.xmlWriters("src/p1.xml", document);
}

使用dom4j实现修改节点的操作

修改第一个p1下面的age元素的值<age>30</age>

// 修改第一个p1下面的age元素的值<age>30</age>
public static void modifyAge() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点
     * 4.得到第一个p1
     * 5.获取p1下面的age元素
     * 6.修改age的值
     * 7.回写xml
     */
    Document document = Dom4jUtils.getDocument(Dom4jUtils.PATH);
    Element root = document.getRootElement();
    Element p1 = root.element("p1");
    Element age = p1.element("age");
    age.setText("30");
    Dom4jUtils.xmlWriters(Dom4jUtils.PATH, document);
}

使用dom4j实现删除节点的操作

  • 删除第一个p1下面的<school>ecit</school>元素
    • 创建解析器
    • 得到document
    • 得到根节点
    • 得到第一个p1
    • 获取第一个p1下面的school元素
    • 回写xml
// 删除第一个p1下面的<school>ecit</school>元素
public static void removeSchool() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点
     * 4.得到第一个p1
     * 5.获取第一个p1下面的school元素
     * 6.p1下删除school
     * 7.回写xml
     */
    Document document = Dom4jUtils.getDocument(Dom4jUtils.PATH);
    Element root = document.getRootElement();
    Element p1 = root.element("p1");
    Element shcool = p1.element("school");
    p1.remove(shcool);
    Dom4jUtils.xmlWriters(Dom4jUtils.PATH, document);
}

使用dom4j获取属性的操作

  • 获取第一个p1里面的属性id1的值
    • 元素.attributeValue(“属性名称”);
// 获取第一个p1里面的属性id1的值
public static void getValues() throws Exception {
    /*
     * 1.创建解析器
     * 2.得到document
     * 3.得到根节点
     * 4.得到第一个p1
     * 5.获取第一个p1的属性值
     */
    Document document = Dom4jUtils.getDocument(Dom4jUtils.PATH);
    Element root = document.getRootElement();
    Element p1 = root.element("p1");
    String s = p1.attributeValue("id1");
    System.out.println(s);
}

使用dom4j来支持xpath的操作

可以直接获取到某个元素

  • 第一种形式:/AAA/DDD/BBB 表示一层一层的 AAA下的DDD下的BBB
  • 第二种形式://BBB 表示只要名称是BBB都可得到
  • 第三种形式:/* 表示所有元素
  • 第四种形式:BBB[1] 表示第一个BBB元素;BBB[last()] 表示最后一个BBB元素
  • 第五种形式://BBB[@id] 表示只要BB元素上有id属性,都得到
  • 第六种形式://BBB[@id=’b1’] 表示元素名称是BBB,在BBB上面有id属性,id属性是b1

使用dom4j支持xpath具体操作

  • 默认的情况下,dom4j不支持xpath,需要引入支持xpath的jar包 使用jaxen-1.1-beta-6.jar
  • 在dom4j里面提供了两个方法来支持xpath
    • selectNodes(“xpath表达式”) 获取多个节点
    • selectSingleNode(“xpath表达式”) 获取一个节点
  • 使用xpath实现查询xml里面所有的name值
    • 所有name元素的xpath表示 //name
// 使用xpath实现查询xml中所有的name值
public static void test1() throws Exception {
    /*
     * 1.得到document
     * 2.直接使用selectNodes("//name")得到所有name元素
     */
    Document document = Dom4jUtils.getDocument(Dom4jUtils.PATH);
    List<Node> list = document.selectNodes("//name");
    for (Node node : list) {
        System.out.println(node.getText());
    }
}
  • 使用xpath实现获取第一个p1下name的值
    • //p1[@id1=’AAA’]/name
// 使用xpath实现获取第一个p1下name的值
public static void test2() throws Exception {
    /*
     * 1.得到document
     * 2.直接使用selectSingleNode("//p1[@id='AAA']/name")
     */
    Document document = Dom4jUtils.getDocument(Dom4jUtils.PATH);
    Node node = document.selectSingleNode("//p1[@id1='AAA']/name");
    System.out.println(node.getText());
}

实现简单的学生管理系统

使用xml当作数据库,存储学生信息

  • 增加操作
  • 删除操作
  • 查询操作
// student.xml
<?xml version="1.0" encoding="UTF-8"?>
<student> 
  <stu> 
    <id>100</id>  
    <name>zhangsan</name>  
    <age>20</age> 
  </stu>  
  <stu> 
    <id>101</id>  
    <name>lisi</name>  
    <age>30</age> 
  </stu> 
</student>
// Student类
public class Student {
    private String id;
    private String name;
    private String age;

    // 省略getter和setter...
}
package cn.itcast.service;

import java.io.FileOutputStream;
import java.util.List;

import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.Node;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.SAXReader;
import org.dom4j.io.XMLWriter;

import cn.itcast.vo.Student;

public class StuService {
    // 增加
    public static void addStu(Student stud) throws Exception{
        /*
         * 1.创建解析器
         * 2.得到document
         * 3.获取根节点
         * 4.在根节点上创建stu标签
         * 5.在std标签上依次添加id name age
         * 6.在id name age上依次添加值
         * 7.回写xml
         */
        SAXReader saxReader = new SAXReader();
        Document document = saxReader.read("src/student.xml");
        Element root = document.getRootElement();
        Element stu = root.addElement("stu");
        Element id = stu.addElement("id");
        Element name = stu.addElement("name");
        Element age = stu.addElement("age");
        id.setText(stud.getId());
        name.setText(stud.getName());
        age.setText(stud.getAge());
        OutputFormat format = OutputFormat.createPrettyPrint();
        XMLWriter xmlWriter = new XMLWriter(new FileOutputStream("src/student.xml"), format);
        xmlWriter.write(document);
        xmlWriter.close();
    }
    // 删除 根据学生的id删除
    public static void delStu(String id) throws Exception{
        /*
         * 1.创建解析器
         * 2.得到document
         * 3.获取所有id 使用xpth //id 
         * 4.遍历list集合
         * 5.判断集合id与传递id是否相同
         * 6.如果相同,把所在id的stu删除
         */
        SAXReader saxReader = new SAXReader();
        Document document = saxReader.read("src/student.xml");
        List<Node> list = document.selectNodes("//id");
        for (Node node : list) {
            String idv =  node.getText();
            if (id.equals(idv)) {
                Element stu  = node.getParent();
                Element stud  = stu.getParent();
                stud.remove(stu);
            }
        }
        OutputFormat format = OutputFormat.createPrettyPrint();
        XMLWriter xmlWriter = new XMLWriter(new FileOutputStream("src/student.xml"), format);
        xmlWriter.write(document);
        xmlWriter.close();
    }
    // 查询 根据id查询学生的信息
    public static Student getStu(String id)  throws Exception{
        /*
         * 1.创建解析器
         * 2.得到document
         * 3.获取所有id 使用xpth //id 
         * 4.遍历list集合
         * 5.判断集合id与传递id是否相同
         * 6.如果相同,得到所在的stu
         * 7.通过stu得到 name age
         */

        SAXReader saxReader = new SAXReader();
        Document document = saxReader.read("src/student.xml");
        Student student = new Student();
        List<Node> list = document.selectNodes("//id");
        for (Node node : list) {
            String idv =  node.getText();
            if (id.equals(idv)) {
                Element stu  = node.getParent();
                Element name = stu.element("name");
                Element age = stu.element("age");
                student.setId(idv);
                student.setName(name.getText());
                student.setAge(age.getText());
            }
        }
        return student;
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值