sql-server - 了解奇怪的数据库 key 设计

标签 sql-server database

背景

对于我们支持并编写 SQL 报告的主要供应商提供的产品,我无法理解数据库中的主键选择。一些不相​​关的细节已更改。

每个主表都有一个唯一的自动编号“内部 ID”字段,但这个字段并不总是用作主键。

我的问题

特别是,我对订单和订单行表的主键选择感到困惑:

  • 组织 PK(organization_internal_id)
  • 订单表 PK (organization_internal_id, order_internal_id)
  • 订单行 PK (order_internal_id, organization_internal_id)

每个订单和订单行表都有一个 internal_id 也唯一标识它们的行。每个表都使用聚集索引的主键。仅内部 ID 就有非聚集索引。

为什么不将内部 ID 设为主键,而是为每个 ID 设置一个单独的唯一聚集索引(就像现在这样)?

一种可能

我能想到的一件事是设计者不知道主键和聚簇索引之间的区别,所以使用一个奇怪的 PK 来获得他们想要的聚簇索引。公平地说,订单行通常引用订单进行访问,并且没有低于行级别的详细信息来引用 order_line_internal_id

查询效率

订单的聚集索引的一个问题是它鼓励 QO 在将许多订单和订单行连接在一起时使用扫描和散列连接(不幸的是,这种情况太常见了,即使我只使用了 5%最后的数据)。选择的行太多,无法在订单行表中循环查找(尽管强制这样做有时会有所帮助),并且使组织成为订单键的第一部分可以防止合并连接在没有排序的情况下工作。

更多详情

  • 这些内部 ID 仅用于连接其他表;对于系统外部的引用或向用户显示的引用,有单独的外部 ID。设计师喜欢这些自动编号人工键。
  • 数据库在 MS SQL Server 2000 上
  • 我认为供应商过去支持 Oracle 作为数据库
  • 订单表有 1M 行 ~5MB
  • 订单行表有 30M 行 ~1GB
  • 整个数据库约为 100GB

最佳答案

另外,考虑到内部 ID 可能是该公司产品中使用的 ORM 所必需的,该数据库随附于此数据库。

关于sql-server - 了解奇怪的数据库 key 设计,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1272245/

相关文章:

sql - 获取不同记录的问题(分组依据)

c# - 让 SQL 连接保持打开状态有什么缺点?

java - 从数据库检索值并将其返回给调用方法

javascript - 在phonegap应用程序中将数据库保存在哪里

php - 从多个表复制数据并插入到一个表中?

php - Mysql的select返回了多少行?

sql - 将 SQL Server 中的 XML 查询结果分配给 XML 类型变量会产生错误

c# - 多次插入需要设置 Id 属性吗?

sql - 如何使用 SQL Server 选择日期时间日期为 dddd、dd mmmm、yyyy?

java - 使用java向mysql插入数据失败