数据模型
数据模型与查询语言
数据模型可能是软件开发中最重要的部分了,它们不仅仅影响着软件的编写方式,而且影响着我们的解题思路。多数应用使用层层叠加的数据模型构建。对于每层数据模型的关键问题是:它是如何用低一层数据模型来表示的?例如:
- 作为一名应用开发人员,你观察现实世界(里面有人员,组织,货物,行为,资金流向,传感器等
) ,并采用对象或数据结构,以及操控那些数据结构的API 来进行建模。那些结构通常是特定于应用程序的。 - 当要存储那些数据结构时,你可以利用通用数据模型来表示它们,如
JSON 或XML 文档,关系数据库中的表、或图模型。 - 数据库软件的工程师选定如何以内存、磁盘或网络上的字节来表示
JSON/XML/ 关系/ 图数据。这类表示形式使数据有可能以各种方式来查询,搜索,操纵和处理。 - 在更低的层次上,硬件工程师已经想出了使用电流,光脉冲,磁场或者其他东西来表示字节的方法。
一个复杂的应用程序可能会有更多的中间层次,比如基于
数据模型的演化
在历史上,数据最开始被表示为一棵大树(层次数据模型
那时人们提出了各种不同的解决方案来解决层次模型的局限性。其中最突出的两个是关系模型(relational model
网络模型
网络模型由一个称为数据系统语言会议(CODASYL)的委员会进行了标准化,并被数个不同的数据库商实现
网络模型中记录之间的链接不是外键,而更像编程语言中的指针(同时仍然存储在磁盘上
最简单的情况下,访问路径类似遍历链表:从列表头开始,每次查看一条记录,直到找到所需的记录。但在多对多关系的情况中,数条不同的路径可以到达相同的记录,网络模型的程序员必须跟踪这些不同的访问路径。
尽管手动选择访问路径够能最有效地利用
关系模型
相比之下,关系模型做的就是将所有的数据放在光天化日之下:一个 关系(表)只是一个 元组(行)的集合,仅此而已。如果你想读取数据,它没有迷宫似的嵌套结构,也没有复杂的访问路径。你可以选中符合任意条件的行,读取表中的任何或所有行。你可以通过指定某些列作为匹配关键字来读取特定行。你可以在任何表中插入一个新的行,而不必担心与其他表的外键关系。
在关系数据库中,查询优化器自动决定查询的哪些部分以哪个顺序执行,以及使用哪些索引。这些选择实际上是“访问路径”,但最大的区别在于它们是由查询优化器自动生成的,而不是由程序员生成,所以我们很少需要考虑它们。如果想按新的方式查询数据,你可以声明一个新的索引,查询会自动使用最合适的那些索引。无需更改查询来利用新的索引。关系模型因此使添加应用程序新功能变得更加容易。
关系数据库的查询优化器是复杂的,已耗费了多年的研究和开发精力。关系模型的一个关键洞察是:只需构建一次查询优化器,随后使用该数据库的所有应用程序都可以从中受益。如果你没有查询优化器的话,那么为特定查询手动编写访问路径比编写通用优化器更容易——不过从长期看通用解决方案更好。
文档模型与图模型
新的非关系型“NoSQL”数据存储在两个主要方向上存在分歧:
- 文档数据库的应用场景是:数据通常是自我包含的,而且文档之间的关系非常稀少。
- 图形数据库用于相反的场景:任意事物都可能与任何事物相关联。
一个方面,文档数据库还原为层次模型:在其父记录中存储嵌套记录(典型的一对多关系,如某个
文档数据库和图数据库有一个共同点,那就是它们通常不会为存储的数据强制一个模式,这可以使应用程序更容易适应不断变化的需求。但是应用程序很可能仍会假定数据具有一定的结构;这只是模式是明确的(写入时强制)还是隐含的(读取时处理)的问题。
其他数据模型
每个数据模型都具有各自的查询语言或框架,我们讨论了几个例子:SQL,MapReduce,
虽然我们已经覆盖了很多层面,但仍然有许多数据模型没有提到。举几个简单的例子:
-
使用基因组数据的研究人员通常需要执行序列相似性搜索,这意味着需要一个很长的字符串(代表一个
DNA 分子) ,并在一个拥有类似但不完全相同的字符串的大型数据库中寻找匹配。这里所描述的数据库都不能处理这种用法,这就是为什么研究人员编写了像GenBank 这样的专门的基因组数据库软件的原因。 -
粒子物理学家数十年来一直在进行大数据类型的大规模数据分析,像大型强子对撞机(LHC)这样的项目现在可以工作在数百亿兆字节的范围内!在这样的规模下,需要定制解决方案来阻住硬件成本的失控。
-
全文搜索可以说是一种经常与数据库一起使用的数据模型。信息检索是一个很大的专业课题,我们不会在本书中详细介绍,但是我们将在第三章和第三章中介绍搜索索引。