我有一个查询,希望以最快的速度执行。
这里是:
select d.InvoiceDetailId,a.Fee,a.FeeTax
from InvoiceDetail d
LEFT JOIN InvoiceDetail a on a.AdjustDetailId = d.InvoiceDetailId
我在 AdjustDetailId 列上放置了一个升序索引
然后我使用“显示实际执行计划”运行查询,结果估计子树成本(最顶层选择节点)为 2.07
然后我想,也许我可以做些事情来改善这一点,所以我在左连接中添加了一个条件,如下所示:
select d.InvoiceDetailId,a.Fee,a.FeeTax
from InvoiceDetail d
LEFT JOIN InvoiceDetail a on a.AdjustDetailId is not null
and a.AdjustDetailId = d.InvoiceDetailId
我重新运行,结果发现子树成本为 0.98。所以我想,太好了,我把它快了两倍。好吧,我接着点击了“显示客户端统计信息”,然后对两个查询点击了 4-5 次“执行”,信不信由你,第一个查询的平均速度更快。我不明白。顺便说一下,查询返回了 120K 行。
有什么见解吗?
也许我因为缓存而得到了受污染的结果,但我不知道是否是这种情况或如何重置缓存。
编辑:好的,我在谷歌上搜索了如何清除查询缓存,所以我在查询前添加了以下内容:
DBCC DROPCLEANBUFFERS
DBCC FREEPROCCACHE
然后我运行每个查询 5 次,第一个查询仍然快一点(13%)。第一个查询:客户端处理时间:239.4 第二个查询:客户端处理时间:290
所以我想问题是,你为什么这么认为?当表的大小增加四倍时,第二个查询会更快吗?或者左连接导致查询两次命中索引,因此它总是会变慢。
请不要责骂我,我只是想学习知识。
答案1
在 AdjustDetailID 的索引中,包括 Fee 和 FeeTax 列。否则系统将需要查找以获取该数据,并且系统最终可能会进行扫描,而忽略您的索引。