2

如果我有一个在三列上定义主键的表,那么为三列中的每一列创建单独的附加索引有什么意义吗?

我在一个客户站点遇到了一个数据库,他们已经这样做了,在我看来这会适得其反,因为这些列已经由聚集的 PK 索引编入索引,并且进一步的索引会增加插入开销而不会提高搜索性能。

但是数据库是一种魔法,所以在提出建议之前,我想从专家那里获得更广泛的意见。

主要关注的是 Sql Server,但这种情况也可能出现在使用 Oracle 的站点上。

4

3 回答 3

3

所以你有一个包含两列或更多列的索引键。对于此类索引,列的顺序很重要。

例如:如果索引键是(ColA,ColB,ColC)( CREATE INDEX MyIndexName ON MySchema.Mytable(ColA,ColB,ColC) ...),则 SQL Server(默认情况下)不能跳过第一列 ( ColA) 来查找第二列 ( ColB)。对于复合索引,如果在前面的列上存在相等的谓词(通常具有此模板<Column> = <Constant>,但也阅读我的答案的最后一段),SQL Server 可以在列上查找:

[1] Are SARGable <=> index seek以下谓词(只是几个例子)

WHERE ColA=@p1
WHERE ColA<=@p1
WHERE ColA>@p1
WHERE ColA=@p1 AND ColB=@p2
WHERE ColA=@p1 AND ColB=@p2 AND ColC=@p3
WHERE ColA=@p1 AND ColB=@p2 AND ColC<=@p3
WHERE ColA=@p1 AND ColB=@p2 AND ColC>@p3
.. For a complete picture please read SQLMag article from the last paragraph

[2] 以下谓词不是 SARGable 或不完全 SARGable (仅举几个例子)

WHERE ColB=@p2因为在上一列中缺少相等的谓词: ColA 在这种情况下,具有此键的索引(ColB)可能很有用。

WHERE ColA>=@p1 AND ColB=@p2因为第一列没有相等的谓词:ColA。在这种情况下,具有此键的索引(ColB,ColA)可能很有用。

WHERE ColA=@p1 AND ColB<=@p2 AND ColC=@p3因为第二列 ( ColB) 上的谓词不相等。在这种情况下,具有这些键之一的索引(ColA,ColC,ColB)(ColC,ColA,ColB)可能很有用。

有关此主题的更多信息(SARGable):链接

这意味着如果您有一个带有此键的索引,那么(ColA,ColB,ColC)这些索引(ColB)、或也可能有用。(ColB,ColA)(ColA,ColC,ColB)(ColC,ColA,ColB)

于 2013-07-25T13:47:35.650 回答
1

根据您的应用程序,您可以决定最适合表中其他列的索引的方法。例如,如果您有很大比例的查询包括某些列,则将它们作为索引包含可能是有意义的。您可以为每列包含一个索引,或者创建一个“覆盖索引”,其中可能包含您知道将在 SQL 查询中经常由您的应用程序返回的其他列。

以下是一些其他有用的建议:

  1. 您可以运行 SQL Management Studio 并使用“显示估计的执行计划”发出一些 SELECT/INSERT/UPDATE/DELETE 查询。这将为您提供 DBMS 在幕后工作的可视化图表。如果您看到“表扫描”或“索引扫描”,您可以通过添加索引以更改为“表搜索”或“索引搜索”来提高性能,这会更有效。

  2. 您可以安装一个名为SQL Performance Dashboard的工具。这是一个由 Microsoft 提供的出色工具,它将实际检查应用程序中针对您的数据库的查询/事务,并提供 SSRS 报告以及在何处添加索引等的建议提示。仪表板报告可用于 SQL Server 2008 及更高版本.

于 2013-07-25T13:24:38.860 回答
1

要在本问题的正文中回答您的问题,是的,即使该列是主键的一部分,为仅一列创建索引也有一点(实际上是几个)。这样的一点是数据库引擎可以使用更具选择性的索引,特别是如果只有该选择性索引中的列与正在执行的查询或命令相关。可以使用更具选择性的索引的一个原因是,对于具有多列的索引,索引中列的顺序很重要;如果第一列不相关,则不一定(容易)使用多列索引。

于 2013-07-25T13:26:52.553 回答