为了灵活实现的不同路径执行不同的资源,使用xml进行配置。
限定XML内容:XML约束(DTD或schema)。
获得XML内容:dom4j解析。
XML
语法上与HTML相似,区别在于HTML的标签时固定的,而XML标签没有固定,但有自己的限制。
更多使用在配置文件中,比较小,轻量级。
XML不是HTML的替代,而是对HTML的补充。
语法
声明
//以问号开头和结尾,version必须有
//verson:XML版本,必须属性 1.0
//encoding:文档的编码 默认utf-8
<!--
以问号开头和结尾,version必须有
verson:XML版本,必须属性 1.0
encoding:文档的编码 默认utf-8
-->
<?xml version="1.0" encoding="UTF-8"?>
文档声明必须从文档的0行0列位置开始。
元素
<servlet>
<!--
1、区分大小写
2、不能使用空格,不能使用冒号
3、不能使用xml开头
-->
格式化良好的XML文档,必须只有一个根元素。
属性
<!-- 固定格式:属性名="属性值" -->
<web-app version="2.5">
属性是元素的一部分,必须出现在元素的开始标签中。一个元素中不能出现同名属性。属性名不能使用特殊字符,且必须字母开头。
注释
<!-- 这是注释 -->
转义字符
CDATA区
<!-- 大量的转义字符出现在xml文档时,可以用CDATA -->
<![CDATA [
任意内容
] ]>
DTD约束
document type definition. 文档类型定义,用来约束xml文档。一般都是别人提供的。
DTD语法
文档声明
1、内部DTD,在xml文档内部嵌入DTD,只对当前xml有效。
2、外部DTD—本地DTD,DTD文档在本地系统上,公司内部自己项目使用。(SYSTEM)
3、外部DTD—公共DTD,DTD文档在网络上,一般都有框架提供。(PUBLIC)
元素声明
例子
<?xml version="1.0" encoding="UTF-8"?>
<!--
模拟servlet2.3规范,如果开发人员需要在xml使用当前DTD约束,必须包括DOCTYPE。
格式如下:
<!DOCTYPE web-app SYSTEM "web-app_2_3.dtd">
-->
<!ELEMENT web-app (servlet*,servlet-mapping* , welcome-file-list?) >
<!ELEMENT servlet (servlet-name,description?,(servlet-class|jsp-file))>
<!ELEMENT servlet-mapping (servlet-name,url-pattern+) >
<!ELEMENT servlet-name (#PCDATA)>
<!ELEMENT servlet-class (#PCDATA)>
<!ELEMENT url-pattern (#PCDATA)>
<!ELEMENT description (#PCDATA)>
<!ELEMENT jsp-file (#PCDATA)>
<!ELEMENT welcome-file-list (welcome-file+)>
<!ELEMENT welcome-file (#PCDATA)>
<!ATTLIST web-app version CDATA #IMPLIED>
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE web-app SYSTEM "web-app_2_3.dtd">
<web-app version="1.0">
<servlet>
<servlet-name></servlet-name>
<servlet-class></servlet-class>
</servlet>
<servlet-mapping>
<servlet-name></servlet-name>
<url-pattern></url-pattern>
</servlet-mapping>
<welcome-file-list>
<welcome-file></welcome-file>
</welcome-file-list>
</web-app>
以改约束下的xml文件必须限定在约束内,不能自定义其他的标签了。
Schema约束
比DTD强大,是DTD的替代者。它本身也是xml文档,但拓展名为xsd,而不是xml。拥有更完善的数据类型。
同样,如果使用约束,直接引用就可以了。
支持命名空间
用来处理元素和属性的名称冲突情况。
<!-- 出现两个table,指明来处,使用显式命名空间,对table进行前缀 -->
<h:table>
<h:tr>
<h:td>Apples</h:td>
<h:td>Bananas</h:td>
</h:tr>
</h:table>
<f:table>
<f:name>African Coffee Table</f:name>
<f:width>80</f:width>
<f:length>120</f:length>
</f:table>
XML解析
解析方式
1、DOM解析:将文档一次性加载到内存中形成树结构,进行解析,形成一个Document对象。
缺点:如果文档特别大,容易导致内存溢出。
优点:方便树结构,进行增删改查。
2、SAX解析:边读边解析。
缺点:不支持增删改查
优点:不会出现内存溢出
解析器
常用dom4j,JAXP。
使用API
1、导入jar包
2、dom4j必须使用核心类SaxReader加载xml文档获得Document对象,通过Document对象获得文档根元素,进行操作。
public void doemo() throws Exception{
//获得Document
SAXReader saxreader = new SAXReader();
Document document = saxReader.read("src/cn/itcast/a_xml/web.xml");
//获得根元素
Element rootElement = document.getRootElement();
//获取所有子元素
List<Element> allchildElement = rootElement.elements();
}
demo
public class TestMyServlet {
@Test
public void testMyServlet(){
try {
//1.创建解析器对象
SAXReader saxReader = new SAXReader();
//2.使用解析器加载web.xml文件得到document对象
Document document = saxReader.read("src/cn/itheima/web/servlet1/web.xml");
//3.获取根元素节点
Element rootElement = document.getRootElement();
//4.根据元素名称获取子元素节点
Element servletElement = rootElement.element("servlet");
//5.根据元素名称获取servlet-class的文本节点
String servletClass = servletElement.element("servlet-class").getText();
//System.out.println(servletClass);
//6.通过类全名获取字节码文件
Class clazz = Class.forName(servletClass);
//7.创建实例对象
MyServlet1 my = (MyServlet1) clazz.newInstance();
//8.调用实例对象里面的方法
my.init();
my.service();
my.destory();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
package cn.itheima.web.servlet1;
public class MyServlet1 implements IMyServlet{
@Override
public void init() {
System.out.println("MyServlet1诞生了……");
}
@Override
public void service() {
System.out.println("MyServlet1开始服务了……");
}
@Override
public void destory() {
System.out.println("MyServlet1销毁了……");
}
}
package cn.itheima.web.servlet1;
public interface IMyServlet {
public void init();
public void service();
public void destory();
}
这里需要用到反射来完成类的加载工作!!! 通过xml调用某个类。