我有一个名为Workflow的表。它有37M行。ID列上有一个主键(int),外加一个附加列。ID列是索引中的第一列。
如果我执行以下查询,则不使用PK (除非我使用索引提示)
Select Distinct(SubID) From Workflow Where ID >= @LastSeenWorkflowID如果我执行此查询,则使用PK
Select Distinct(SubID) From Workflow Where ID >= 786400000我怀疑问题出在查询中使用参数值(我必须这么做)。我真的不想使用索引提示。有解决这个问题的办法吗?
发布于 2011-07-08 23:05:26
生成的计划必须在这两种情况下都有效。有一个阈值,在这个阈值上,对聚集索引的范围搜索比对非聚集索引的完全扫描更昂贵,原因很简单,因为聚集索引非常宽(它包括叶级别中的每一列),因此有如此多的页面要迭代。
您可以提供一个专门针对此查询的窄索引:
CREATE INDEX WorkflowSubId ON Workflow(ID, SubId);或者:
CREATE INDEX WorkflowSubId ON Workflow(ID) INCLUDE (SubId);发布于 2011-07-08 08:38:45
假设你的PK是一个身份或者总是大于0,也许你可以尝试这样做:
Select Distinct(SubID)
From Workflow
Where ID >= @LastSeenWorkflowID
And ID > 0通过添加第二个条件,可能会导致优化器使用索引查找。
发布于 2011-07-15 23:44:23
这是一个典型的局部变量产生次优计划的例子。
您应该使用OPTION (重新编译)来使用ID的实际参数值来编译您的查询。
有关更多信息,请参阅我的博客:http://www.sqlbadpractices.com/using-local-variables-in-t-sql-queries/
https://stackoverflow.com/questions/6615792
复制相似问题