由于是白话讲解, 所以其准确性将不够严谨,很多时候需要意会,如果都用严谨的数学语言,那文档读起来就很冗长,复杂且不好读了!
正是为了简明扼要,有时可以适当失却一些严谨,但不能影响结果的正确性.
记得我做得一个项目,负责显示,底层负责上数据.把几百上千个模块数据传上来.
可是接口竟然是二进制的. 他们把数据说明书给我, 让我按字节,甚至按bit 解析数据。
这倒也没什么,很多文件格式及其一些二进制流文件不都是这么干的吗. 这到是,不过
有两个缺点:
1. 数据错位一个byte那所有的数据就全部会解析错误。就是说一个模块的错误会传递到所有模块,因为数据本身是没有模块的分界的。
2. 每增加一类模块,就要再给我一个说明书,让我按要求来解析. 是的,没有办法,因为新的模块又有新的数据格式.
我又想起了我们游戏组开发游戏,每个人负责一个节目,有一个人负责打印驱动,打印节目图片时,也采用了二进制接口,每个人书写自己的数据说明,交给打印。
负责打印的人也很烦啊,我给你们接口你们自己调用吧。但是这帮搞游戏的人也很忙啊,那有比二进制交出去更简单的方式呢。
这里就是一个数据交互的问题.
xml 就很好的解决了这个问题,它以文本方式解决了结构化数据传输问题.
TiXML 代码阅读: 需要了解几个概念:
从简单到复杂:
Xml 注释是以 结尾的部分
注释是一个结点,注释存在的意义只是为了人们阅读时提供额外说明信息帮助人理解
举例:
追踪代码: TiXmlComment:
我不能把一大批类函数,类成员及基类一股脑copy, 那效率太低,也不得要领,你可以如此浏览一下代码.
Parse 结果,会把注释部分信息保存到 value 中, value是其父类TiXmlNode 中定义的.
代码定义:(简化版)
type = class TiXmlComment : public TiXmlNode {
}
Xml 声明是以 为结尾的部分. 可以包含3个属性,version,encoding,standalone.
声明是一个结点,声明是为了说明本xml协议所使用的版本,编码及是否是单独的信息
它是可选的. 如果有,也只有一个.
举例:
TiXmlDelaration 也继承自TiXmlNode, 这个对象Parse 的结果会保留在version,encoding,standalone中,
返回的node 保存到node 链表
代码定义:(简化版)
type = class TiXmlDeclaration : public TiXmlNode {
private:
std::string version;
std::string encoding;
std::string standalone;
}
用=分割的两个部分,前面为name,后面为value,value 用双引号或单引号包裹. 键值对可以有多个.
举例: 上面的 version="1.0",
继承自TiXmlBase, 有name,value值,有prev,next 指针.
其 Parse 函数会保留name,value 的值到其成员变量.
属性不是一个结点,但继承子TiXmlBase, 属性是键值对。
type = class TiXmlAttribute : public TiXmlBase {
private:
TiXmlDocument *document;
std::string name;
std::string value;
TiXmlAttribute *prev;
TiXmlAttribute *next;
}
Xml 元素是以< 开始的, 不是声明和注释,也不是 元素是以<开始后跟alpha 字母或下画线,然后跟若干个(0个或多个) alpha 字符或下滑线或数字或连字符(-_. 不能有其它字符. 元素可以有0个1个或多个属性,
元素的名称以>代表结束. 后面为元素的value, value 可以包含文本,可以嵌套 XML 元素
value的结尾为配对的元素结尾标识,开始后跟元素的名称。
Xml文档 必需要有一个根元素.
元素的概念是理解xml的关键!
举例:
…
4.1. TiXmlElement::Parse 函数
元素是以< 开始的,首先它会读取名字,若名字后面有属性,则读取属性,直到>为止,
然后读取value.
4.2 什么是XMl 元素的value TiXmlElement::ReadValue
4.2.1 : value 可以嵌套元素 以<为元素开始, 为元素结尾
4.2.2 : 如果不是元素,那就是Text, 读取文本
代码定义: Xml 元素是一个结点, 并包含属性集合.(简化版,忽略成员函数等)
type = class TiXmlElement : public TiXmlNode {
private:
TiXmlAttributeSet attributeSet;
}
XML文档是有可选的声明,一个根元素下辖0个1个或多个子元素来构成。
所以XML doc 是一个结点的集合,它把声明,注释,根元素及子元素有机的集中在一起。
但它们的有机集合是TiXmlNode 之功,而不是Doc 特意安排的.
代码定义(简化版), 说明Doc 仅仅是一个Node 而以.
type = class TiXmlDocument : public TiXmlNode {
private:
int errorId;
std::string errorDesc;
int tabsize;
TiXmlCursor errorLocation;
}
代码中是如下定义的,只给出了成员变量部分. 成员函数部分忽略.
type = class TiXmlNode : public TiXmlBase {
protected:
TiXmlNode *parent;
TiXmlNode::NodeType type;
TiXmlNode *firstChild;
TiXmlNode *lastChild;
std::string value;
TiXmlNode *prev;
TiXmlNode *next;
}
给一个例子:
parent = 0x7fffffffdcc0,
type = TiXmlNode::TINYXML_DECLARATION,
firstChild = 0x0,
lastChild = 0x0,
value = "",
prev = 0x0,
next = 0x0
5个成员都是指针,为得是保持与其它node 的关系,有一个属性类型何一个value字符串类型.
小结: xml 就是引入元素的概念来划分数据, 元素用<做引导,以>表示结尾, 元素当然有名称,
可以有属性,可以有Text文本作为其子结点或嵌套其它元素作为子结点.