复合索引主键与唯一自增主键

Posted

技术标签:

【中文标题】复合索引主键与唯一自增主键【英文标题】:Composite Index primary key vs Unique auto increment primary key 【发布时间】:2011-06-27 11:20:20 【问题描述】:

我们有一个超过 1.11 亿行的事务表,它的聚集复合主键为...

RevenueCentreID  int
DateOfSale       smalldatetime
SaleItemID       int
SaleTypeID       int

...在 SQL 2008 R2 数据库中。

我们将很快为归档项目截断并重新填充表,因此一旦表被截断,就有机会正确获取索引。 保留复合主键会更好,还是应该使用唯一的自动增量主键?

对表格的大多数搜索都是使用 DateOfSale 和 RevenueCentreID 列完成的。我们也经常加入 SaleItemID 列。我们很少使用 SaleType 列,实际上它只是包含在主键中以实现唯一性。我们不关心插入和删除新的销售数据需要多长时间(一夜之间完成),而是返回报告的速度。

【问题讨论】:

***.com/questions/6493792/… 【参考方案1】:

代理键在这里没有用处。我建议在列出的列上使用聚簇主键,并在 SaleItemID 上使用索引。

【讨论】:

我同意它在强制唯一性和参照完整性方面是多余的。但是,使用单个值来标识唯一行可以使某些复杂的查询变得更简单。我想说(这是故意多余的)代理键只有在需要查询时才需要。 即使您现在不需要它 - 拥有代理键​​可以让您在将来的某个时候更容易使用 ORM。 @BonyT:ORM 坏了。请参阅here 了解我为什么这么说的详细说明。 @Dems:如果其他关系在代理项上有外键,它只会使查询更简单。由于显然目前在现有的候选键上没有任何东西有外来物,因此情况并非如此。 @Marcelo - 我非常不同意你的说法,但我怀疑我们有着共同的观点。在没有使用 ORM、使用家庭烘焙的 ORM 以及使用 NHibernate 的情况下工作,然后我知道我更喜欢哪个。然而,将 ORM 固定在一个为它设计得很糟糕的模式设计上简直是愚蠢的。就像软件行业中的其他任何东西一样,ORM 是一种工具,任何工具都可能被滥用。【参考方案2】:

你已经知道你想要并且需要一个自然键和一个代理键。

自然键保持业务键的唯一性,非常适合索引。代理键将有助于查询和开发。

因此,在您的情况下,代理自动递增键很好,因为它有助于保持所有数据行的完整性。 DateOfSale、RevenueID 和 ClientID 的自然键将成为确保不存储重复记录并加快查询速度的好方法,因为您可以索引自然键。

【讨论】:

“因此,在您的情况下,代理自动递增键很好,因为它有助于保持所有数据行的完整性。”这意味着什么?如果没有代理 ID 号,行就有散开的危险?【参考方案3】:

如果您不关心插入和删除的速度,那么您可能需要多个精确定位查询的索引。

您可以按照您的建议创建一个自动递增的主键,但也可以根据需要创建索引来覆盖报告查询。在键中当前拥有的列上创建唯一约束以强制唯一性。

索引调整向导将帮助定义最佳索引集,但最好自己创建。

经验法则 - 您可以定义要索引的列,也可以“包含”列。

如果您的报告在列上有 OrderBy 或 Where 子句,那么您需要针对这些定义索引。选择中返回的任何其他字段都应包含在列中。

【讨论】:

以上是关于复合索引主键与唯一自增主键的主要内容,如果未能解决你的问题,请参考以下文章

复合主键?还是具有唯一复合索引的自动增量主键? [关闭]

数据库索引类型

初学者必备:MySQL的主键,外键与唯一约束设置(点赞!!!)

初学者必备:MySQL的主键,外键与唯一约束设置(点赞!!!)

Day903.自增主键不能保证连续递增 -MySQL实战

通俗易懂 索引单列索引复合索引主键唯一索引聚簇索引非聚簇索引唯一聚簇索引 的区别与联系