Rac*_*SQL 1 performance sql-server-2008 sql-server clustered-index query-performance
我有一个查询,即使使用SQL Sentry,也无法消除索引扫描。
这是查询:
SELECT TOP 30 codCliente FROM (
SELECT t1.CodCliente, codcampo, valor, t1.chavealeat
FROM tblCliente AS t1 WITH(NOLOCK)
INNER JOIN tblClienteDetalhe AS t2 WITH(NOLOCK)
ON t1.codcliente = t2.codcliente
AND CodCampo IN(-1, 4)
WHERE codStatus IN (0)
AND t1.ChavePeriodo < GETDATE()
AND t1.CodStatusLigacao = 0
AND EXISTS
(
SELECT codcliente FROM tblclientedetalhe WITH(NOLOCK)
WHERE codcampo = 3 AND valor = '2'
AND codcliente = t1.codcliente
)
AND EXISTS
(
SELECT codcliente FROM tblclientedetalhe WITH(NOLOCK)
WHERE codcampo = 6
AND CONVERT(DATETIME, Valor) BETWEEN '2015-08-01' AND '2015-08-31'
AND DATEDIFF(DAY, Valor, GETDATE()) > 15
AND codcliente = t1.codcliente
)
AND NOT EXISTS
(
SELECT 0 FROM tblPesquisa WITH(NOLOCK)
WHERE tblPesquisa.CodCliente = t1.CodCliente
)
AND EXISTS
(
SELECT codcliente FROM tblclientedetalhe WITH(NOLOCK)
WHERE codcampo = 4 and valor = '202' and codcliente = t1.codcliente
)
) AS Cliente
Pivot (MAX(Valor) FOR codCampo in ([4])) AS PivotTable
WHERE (((([4] = '202'))))
ORDER BY chavealeat;
Run Code Online (Sandbox Code Playgroud)
这是我做的索引:
create index IX_CHAVEALEAT_CODCLIENTE
on tblcliente (chavealeat,codcliente)
include (chaveperiodo,codstatus,codstatusligacao)
Run Code Online (Sandbox Code Playgroud)
而且,这是分析:
为什么显示计划index scan
?我涵盖了所有栏目。我曾经option(recompile)
更新计划。
这个指数有错吗?输出只有codcliente
.
我当时有 10-30 个查询在运行,并且没有 wait_info 问题。
仅仅因为您有一个覆盖索引并不意味着它不会扫描,也不意味着扫描仍然不是访问所请求数据的最佳方式。
你回来了,什么,300 万行?即使这不是表的大部分内容,执行 300 万次查找操作仍然没有多大意义,查找第一行并为其余行执行范围扫描也不可能有任何好处。还有一个问题是多个EXISTS
子句——其中多个子句没有连接到索引的前导键列——不太可能都能够利用搜索的相同输出。并且您对所有INCLUDE
列都有过滤器- 它们不是键的一部分,因此在这些列上查找将很困难(实际上,我见过的唯一一种情况是,当存在索引时仍然使用索引进行查找)WHERE
针对非键列的子句是当列BIT
,并且这些场景没有引入您上面的所有其他变量)。您也在使用PIVOT
和聚合,我确定这无济于事。
另外,什么表CodCampo
在(为什么它没有正确地以表别名作为前缀)?您可能有以下两个问题中的一个或两个:
OR
子句),可以阻止寻求(见保罗在这里的回答)。tblcliente
,那么您的索引无论如何都没有覆盖。您可以尝试使用FORCESEEK
提示运行查询(在 Paul 的示例中也提到过),它要么无法生成计划(不太可能),要么您将获得可以与我们共享的计划,如果您也共享扫描计划,您在没有提示的情况下,我们可以进一步了解 SQL Server 选择扫描的原因。
顺便说一句(这肯定不会帮助您进行搜索),因为估计值要低得多,我会检查您的统计数据是否是最新的。
最后,不要总是假设扫描是不好的,需要消除的东西!在很多情况下,扫描确实是检索数据的最佳方式。