1. DTD基本介绍
xml文件分为两种类型,一个是在好形式,这是well-formed,还有一个合法有效,这是valid。
XML文件遵循-called“好形式”各种语法规则要求,这仅仅是“长征迈出的第一步”。全然意义上的XML文件不仅应该是“形式良好的”。并且还应该是使用了这些自己定义标记的“有效”的XML文件。
一个XML文件必须遵守文件类型描写叙述DTD(DocumentType Definition)中定义的种种规定。DTD实际上是“元标记”这个概念的产物,它描写叙述了一个置标语言的语法和词汇表,也就是定义了文件的总体结构以及文件的语法。
简而言之,DTD规定了一个语法分析器为了解释一个“有效的”XML文件所须要知道的全部规则的细节。
文档类型定义(DTD)可定义合法的XML文档构建模块。它使用一系列合法的元素来定义文档的结构。
DTD 可被成行地声明于 XML 文档中。也可作为一个外部引用。
1.1. 内部的 DOCTYPE 声明
假如 DTD 被包括在您的 XML 源文件里。它应当通过以下的语法包装在一个 DOCTYPE 声明中:
<!DOCTYPE 根元素 [元素声明]> |
带有 DTD 的 XML 文档实例(能够用浏览器打开查看源代码)
学生名冊.xml
<? xml version="1.0" encoding="UTF-8"?> <!DOCTYPE 学生名冊[ <!ELEMENT 学生名冊 (学生+)> <!ELEMENT 学生 (姓名,性别,年龄)> <!ATTLIST 学生 学号 ID #REQUIRED> <!ELEMENT 姓名 (#PCDATA)> <!ELEMENT 性别 (#PCDATA)> <!ELEMENT 年龄 (#PCDATA)> ]> <学生名冊> <学生 学号="a001"> <姓名>张三</姓名> <性别>男</性别> <年龄>27</年龄> </学生> <学生 学号="a002"> <姓名>李四</姓名> <性别>男</性别> <年龄>27</年龄> </学生> <学生 学号="a003"> <姓名>王五</姓名> <性别>男</性别> <年龄>27</年龄> </学生> </学生名冊> |
解释:
<!DOCTYPE 学生名冊[ à指定根元素为学生名冊
<!ELEMENT学生名冊 (学生+)> à指定根元素下有一个或多个学生元
<!ELEMENT学生 (姓名,性别,年龄)> à
<!ATTLIST学生 学号 ID #REQUIRED> à指定学生的属性学号,数据类型为ID,必须
<!ELEMENT姓名 (#PCDATA)> à指定姓名元素下的内容为普通字符串类型
<!ELEMENT性别 (#PCDATA)>
<!ELEMENT年龄 (#PCDATA)>
]>
1.2. 外部文档声明
假如 DTD 位于 XML 源文件的外部,那么它应通过以下的语法被封装在一个 DOCTYPE 定义中:
<!DOCTYPE 根元素 SYSTEM "文件名称"> |
联系人.dtd
<?xml version="1.0" encoding="GB2312"? > <!ELEMENT 联系人列表 (联系人)> <!ELEMENT 联系人 (姓名, ID, 公司, EMAIL, 电话, 地址)> <!ELEMENT 地址 (街道, 城市, 省份)> <!ELEMENT 姓名 (#PCDATA)> <!ELEMENT ID (#PCDATA)> <!ELEMENT 公司 (#PCDATA)> <!ELEMENT EMAIL (#PCDATA)> <!ELEMENT 电话 (#PCDATA)> <!ELEMENT 街道 (#PCDATA)> <!ELEMENT 城市 (#PCDATA)> <!ELEMENT 省份 (#PCDATA)> |
联系人.xml
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE 联系人列表 SYSTEM "联系人列表.dtd"> <联系人列表> <联系人> <姓名>张三</姓名> <ID>001</ID> <公司>微软</公司> <EMAIL>Morris131@163.com</EMAIL> <电话>15873001206</电话> <地址> <街道>芙蓉街</街道> <城市>长沙</城市> <省份>湖南</省份> </地址> </联系人> </联系人列表> |
解释:
<!DOCTYPE 联系人列表 SYSTEM "联系人列表.dtd">将外部dtd文件引入。
1.3. 为什么使用 DTD?
1. 通过 DTD,您的每个 XML 文件均可携带一个有关其自身格式的描写叙述。
2. 通过 DTD,独立的团体可一致地使用某个标准的 DTD 来交换数据。
3. 使用某个标准的 DTD 来验证从外部接收到的数据。
4. 使用 DTD 来验证您自身的数据。
2. XML 构建模块
全部的 XML 文档(以及 HTML 文档)均由下面简单的构建模块构成:
l 元素
l 属性
l 实体
l PCDATA
l CDATA
以下是每一个构建模块的简要描写叙述。
2.1. 元素
元素是 XML 以及 HTML 文档的主要构建模块。
HTML 元素的样例是"body" 和 "table"。XML 元素的样例是 "note" 和 "message" 。元素可包括文本、其它元素或者是空的。空的 HTML 元素的样例是 "hr"、"br" 以及 "img"。
实例
<body>body text in between</body> <message>some message in between</message> |
2.1.1. 声明一个元素
在 DTD 中。XML 元素通过元素声明来进行声明。元素声明使用以下的语法:
<!ELEMENT 元素名称 类别>
或者
<!ELEMENT 元素名称 (元素内容)>
2.1.2. 空元素
空元素通过类别关键词EMPTY进行声明:
<!ELEMENT 元素名称 EMPTY>
样例:
<!ELEMENT br EMPTY>
XML样例:
<br />
2.1.3. 仅仅有 PCDATA 的元素
仅仅有 PCDATA 的元素通过圆括号里的 #PCDATA 进行声明:
<!ELEMENT 元素名称 (#PCDATA)>
样例:
<!ELEMENT from (#PCDATA)>
2.1.4. 带有不论什么内容的元素
通过类别关键词 ANY 声明的元素,可包括不论什么可解析数据的组合:
<!ELEMENT 元素名称 ANY>
样例:
<!ELEMENT note ANY>
2.1.5. 带有子元素(序列)的元素
带有一个或多个子元素的元素通过圆括号里的子元素名进行声明:
<!ELEMENT 元素名称 (子元素名称 1)>
或者
<!ELEMENT 元素名称 (子元素名称 1,子元素名称2,.....)>
样例:
<!ELEMENT note(to,from,heading,body)>
当子元素依照由逗号分隔开的序列进行声明时,这些子元素必须依照同样的顺序出如今文档中。在一个完整的声明中,子元素也必须被声明,同一时候子元素也可拥有子元素。"note" 元素的完整声明是:
<!ELEMENT note(to,from,heading,body)>
<!ELEMENT to (#PCDATA)>
<!ELEMENT from (#PCDATA)>
<!ELEMENT heading (#PCDATA)>
<!ELEMENT body (#PCDATA)>
2.1.6. 声明仅仅出现一次的元素
<!ELEMENT 元素名称 (子元素名称)>
样例:
<!ELEMENT note (message)>
上面的样例声明了:message 子元素必须出现一次,而且必须仅仅在 "note" 元素中出现一次。
2.1.7. 声明最少出现一次的元素
<!ELEMENT 元素名称 (子元素名称+)>
样例:
<!ELEMENT note (message+)>
上面的样例中的加号声明了:message 子元素必须在 "note" 元素内出现至少一次。
2.1.8. 声明出现零次或多次的元素
<!ELEMENT 元素名称 (子元素名称*)>
样例:
<!ELEMENT note (message*)>
上面的样例中的星号声明了:子元素 message 可在 "note" 元素内出现零次或多次。
2.1.9. 声明出现零次或一次的元素
<!ELEMENT 元素名称 (子元素名称?
)>
样例:
<!ELEMENT note (message?)>
上面的样例中的问号声明了:子元素 message 可在 "note" 元素内出现零次或一次。
2.1.10. 声明“非.../既...”类型的内容
样例:
<!ELEMENT note(to,from,header,(message|body))>
上面的样例声明了:"note" 元素必须包括 "to" 元素、"from" 元素、"header" 元素,以及非 "message" 元素既 "body" 元素。
声明混合型的内容
样例:
<!ELEMENT note(#PCDATA|to|from|header|message)*>
上面的样例声明了:"note" 元素可包括出现零次或多次的 PCDATA、"to"、"from"、"header" 或者 "message"。
<TBODY>元 字符 |
含 义 |
+ |
出现一次或多次 |
* |
出现零次或多次 |
? |
可选,不出现或出现一次 |
() |
一组要共同匹配的表达式 |
| |
OR,或 |
。 |
AND,要求严格遵从顺序要求 |
元素A |
元素列表,无须遵从顺序要求</TBODY> |
2.2. 属性
属性可提供有关元素的额外信息。
属性总是被置于某元素的開始标签中。属性总是以名称/值的形式成对出现的。以下的 "img" 元素拥有关于源文件的额外信息:
<img src="computer.gif" /> |
<img src="computer.gif" />元素的名称是"img"。
属性的名称是 "src"。属性的值是 "computer.gif"。因为元素本身为空,它被一个 "/" 关闭。
在DTD 中。属性通过ATTLIST 声明来进行声明。
2.2.1. 声明属性
属性声明拥使用下列语法:
<!ATTLIST 元素名称 属性名称 属性类型 默认值>
DTD 实例:
<!ATTLIST payment type CDATA"check">
XML 实例:
<payment type="check" />
下面是属性类型的选项:
类型 |
描写叙述 |
CDATA |
值为字符数据 (character data) |
(en1|en2|..) |
此值是枚举列表中的一个值 |
ID |
值为唯一的 id |
IDREF |
值为另外一个元素的 id |
IDREFS |
值为其它 id 的列表 |
NMTOKEN |
值为合法的 XML 名称 |
NMTOKENS |
值为合法的 XML 名称的列表 |
ENTITY |
值是一个实体 |
ENTITIES |
值是一个实体列表 |
NOTATION |
此值是符号的名称 |
xml: |
值是一个提前定义的 XML 值 |
默认值參数可使用下列值:
值 |
解释 |
值 |
属性的默认值 |
#REQUIRED |
属性值是必需的 |
#IMPLIED |
属性没必要的 |
#FIXED value |
属性值是固定的 |
2.2.2. 规定一个默认的属性值
DTD:
<!ELEMENT square EMPTY>
<!ATTLIST square width CDATA"0">
合法的 XML:
<square width="100" />
在上面的样例中,"square" 被定义为带有 CDATA 类型的 "width" 属性的空元素。假设宽度没有被设定。其默认值为0 。
2.2.3. #IMPLIED
语法
<!ATTLIST 元素名称 属性名称 属性类型 #IMPLIED>
样例
DTD:
<!ATTLIST contact fax CDATA #IMPLIED>
合法的 XML:
<contact fax="555-667788"/>
合法的 XML:
<contact />
假如您不希望强制作者包括属性,而且您没有默认值选项的话,请使用关键词 #IMPLIED。
2.2.4. #REQUIRED
语法
<!ATTLIST 元素名称 属性名称 属性类型 #REQUIRED>
样例
DTD:
<!ATTLIST person number CDATA#REQUIRED>
合法的 XML:
<person number="5677" />
非法的 XML:
<person />
假如您没有默认值选项,可是仍然希望强制作者提交属性的话,请使用关键词 #REQUIRED。
2.2.5. #FIXED
语法
<!ATTLIST 元素名称 属性名称 属性类型 #FIXED"value">
样例
DTD:
<!ATTLIST sender company CDATA #FIXED"Microsoft">
合法的 XML:
<sender company="Microsoft"/>
非法的 XML:
<sender company="W3School"/>
假设您希望属性拥有固定的值,并不同意作者改变这个值。请使用 #FIXED 关键词。假设作者使用了不同的值,XML 解析器会返回错误。
2.2.6. 列举属性值
语法:
<!ATTLIST 元素名称 属性名称 (en1|en2|..) 默认值>
DTD 样例:
<!ATTLIST payment type (check|cash)"cash">
XML 样例:
<payment type="check" />
或者
<payment type="cash" />
假设您希望属性值为一系列固定的合法值之中的一个。请使用列举属性值。
2.3. 实体
实体是用于定义用于定义引用普通文本或特殊字符的快捷方式的变量。
实体引用是对实体的引用。
实体可在内部或外部进行声明。
2.3.1. 一个内部实体声明
实体是用来定义普通文本的变量。实体引用是对实体的引用。
大多数同学都了解这个 HTML 实体引用:" "。这个“无折行空格”实体在 HTML 中被用于在某个文档中插入一个额外的空格。
当文档被 XML 解析器解析时,实体就会被展开。
以下的实体在 XML 中被提前定义:
实体引用 |
字符 |
< |
< |
> |
> |
& |
& |
" |
" |
' |
' |
语法:
<!ENTITY 实体名称 "实体的值">
样例:
DTD 样例:
<!ENTITY writer "BillGates">
<!ENTITY copyright "CopyrightW3School.com.cn">
XML 样例:
<author>&writer;©right;</author>
凝视: 一个实体由三部分构成: 一个和号 (&), 一个实体名称, 以及一个分号 (;)。
2.3.2. 一个外部实体声明
语法:
<!ENTITY 实体名称 SYSTEM"URI/URL">
样例:
DTD 样例:
<!ENTITY writer SYSTEM "http://www.w3school.com.cn/dtd/entities.dtd">
<!ENTITY copyright SYSTEM"http://www.w3school.com.cn/dtd/entities.dtd">
XML 样例:
<author>&writer;©right;</author>
2.4. PCDATA
PCDATA 的意思是被解析的字符数据(parsedcharacter data)。
可把字符数据想象为 XML 元素的開始标签与结束标签之间的文本。
PCDATA 是会被解析器解析的文本。
这些文本将被解析器检查实体以及标记。
文本中的标签会被当作标记来处理,而实体会被展开。
只是。被解析的字符数据不应当包括不论什么 &、< 或者 > 字符;须要使用 &、< 以及 > 实体来分别替换它们。
2.5. CDATA
CDATA 的意思是字符数据(characterdata)。
CDATA 是不会被解析器解析的文本。
在这些文本中的标签不会被当作标记来对待,当中的实体也不会被展开。
3. 实例
3.1. 动物园实例
<?xml version="1.0" encoding="UTF-8" standalone="yes"? > <!DOCTYPE 动物园 [ <!ELEMENT 动物园 (爬行类, 两栖类, 鸟类, 哺乳类, 鱼类)> <!ELEMENT 爬行类 (动物+)> <!ELEMENT 两栖类 (动物+)> <!ELEMENT 鸟类 (动物+)> <!ELEMENT 哺乳类 (动物+)> <!ELEMENT 鱼类 (动物+)> <!ELEMENT 动物 (#PCDATA)> <!ATTLIST 动物 数量 CDATA #REQUIRED > ]> <动物园> <爬行类> <动物 数量="2">螃蟹</动物> </爬行类> <两栖类> <动物 数量="10">青蛙</动物> </两栖类> <鸟类> <动物 数量="2">乌鸦</动物> <动物 数量="10">鸽子</动物> </鸟类> <哺乳类> <动物 数量="3">绵羊</动物> </哺乳类> <鱼类> <动物 数量="12">鲫鱼</动物> </鱼类> </动物园> |
3.2. 出版社实例
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE 出版社[ <!ENTITY LH "李红"> <!ENTITY ZHL "张宏良"> <!ELEMENT 出版社 (图书+)> <!ELEMENT 图书 (作者+,图片*,内容+,新章节*)> <!ATTLIST 图书 图书号 ID #REQUIRED> <!ELEMENT 作者 (#PCDATA)> <!ELEMENT 图片 (#PCDATA)> <!ELEMENT 内容 (章节,描写叙述)> <!ELEMENT 章节 (#PCDATA)> <!ATTLIST 章节 数目 CDATA #REQUIRED> <!ELEMENT 描写叙述 (文件夹,简单介绍)> <!ELEMENT 文件夹 (#PCDATA)> <!ELEMENT 简单介绍 (#PCDATA)> <!ELEMENT 新章节 (章节,描写叙述)> <!ATTLIST 新章节 加入 (是|不是) "是"> ]> <出版社> <图书 图书号="a01"> <作者>&LH;&ZHL;</作者> <图片></图片> <内容> <章节 数目="20"></章节> <描写叙述> <文件夹></文件夹> <简单介绍></简单介绍> </描写叙述> </内容> <新章节 加入="是"> <章节 数目="1"></章节> <描写叙述> <文件夹></文件夹> <简单介绍></简单介绍> </描写叙述> </新章节> </图书> </出版社> |
版权声明:本文博客原创文章,博客,未经同意,不得转载。