我正在为客户处理的一个 sql 数据库是用一种不寻常的结构创建的。
例如,不要为以下各项设置一个表:
国家,
状态,
城市,
单位(英寸、米、英里/小时)、
他们只有两张桌子:
- 一个用于列表 ID(字段:列表索引和列表名称)。记录前:城市,单位
- 一个用于给定列表中的项目(字段:项目索引、列表项的描述和引用上述相关列表索引的 fk)。记录前:km/h、亚特兰大、英里、巴黎
listitem 表中 id 的序列是这样组织的,以便在一定程度上将 listitem 中不同组的项目分开,以防需要在列表中添加新项目:
Unit 的 Seq 可能从 20000 开始
城市序列可能从 30000 开始
因此,如果需要添加 10 个新单位,则索引可以与其他已创建的单位保持分组,而不会在其他项目(如城市)中溢出。应用层处理每组项目的序列范围。
他们在列表表中有 30 多个这样的列表,并且在项目表中有数千个项目,每个项目都与列表 ID 相关。
我认为这是没有意义的,原因有很多。但他们认为这很有效,因为“我们只有 2 张桌子而不是 30 张桌子”。他们还认为这是一种新颖且有点典型的工作方式。我知道这在技术上是可行的,但我预计这两个表的实现会出现不必要的和多重问题。
我的问题:做上述事情是典型的还是公认的做法?
这是一种已知的模式,但不是一个好的模式,也不是新奇的。虽然可以使应用程序以这种方式运行,但您会错过很多好处。
首先,外键。不能声明对列表表的引用“只能声明 10,000 范围内的 ID”。因此,适当的参照完整性消失了。没有什么可以阻止重达 10 个伦敦并被染成法兰克福的产品。
第二,数据类型。所有列表值数据类型必须是最小公分母。在实践中,这意味着 Unicode。同样,没有什么可以阻止车辆的乘客人数为 {1, 2, 3, Tuesday} 之一。
类似地,长度必须是可以想象的最大长度,而不仅仅是已知的最长。这会在存储、内存消耗等方面产生开销。
第三,您最终可能只有一个表,但该表中仍然有 30 多种实体类型。这些并没有消失。这增加了不必要的认知负担。与其在名为 Cities 的表中查找城市,不如记住它在名为 Lists 的表中,介于 10,000 和 15,000 之间(或者是 20,000 到 30,000?)。
第四,加入失去自我证明。代替
相反,我们有
我知道我更喜欢哪个。
第五,对于单独的表,每个表的键可能是 256 个值的 1 字节整数。当我打赌这将是一个 4 字节的整数时。当然,总体上不是一大堆字节。但是为什么要减少表数而不是字节数呢?
我将在这里停下来,以这个观察结束。没有一个名副其实的 DBMS 会关心其目录中少 30 个表的情况。它对运行时间的影响绝对为零,但会在未来几年困扰维护。