通常,是什么让SQL查询优化器在嵌套循环和散列连接之间做出决定。
发布于 2009-12-30 00:59:28
如果循环中的条件是sargable的,那么索引就是好的,也就是说,NESTED LOOPS可以用来限制记录的数量。
对于这样的查询:
SELECT *
FROM a
JOIN b
ON b.b1 = a.a1
WHERE a.a2 = @myvar,在a前导的情况下,将获取来自a的每条记录,并应找到b中所有对应的记录。
如果b.b1是索引的,并且基数很高,那么NESTED LOOP将是首选方法。
在SQL Server中,这也是执行非等价连接的唯一方法( ON子句中的=条件除外)
如果需要解析所有(或几乎所有)记录,则HASH JOIN是最快的方法。
它从b中获取所有记录,在这些记录上构建一个哈希表,然后从a中获取所有记录,并使用连接列的值作为键来查找哈希表。
NESTED LOOPS花了这段时间:Na * (Nb / C) * R,
其中Na和Nb是a和b中的记录数,C是索引基数,R是行查找所需的常量时间(1是SELECT中的所有字段,WHERE和ORDER BY子句包含在索引中,如果它们是D27,则花费以下时间:
Na + (Nb * H)
,其中H是构建和查找哈希表所需的常量之和(每条记录)。它们被编程到引擎中。
SQL Server使用表统计信息计算基数,计算并比较这两个值,然后选择最佳方案。
发布于 2009-12-30 00:55:36
通常,它将依赖于要连接的集合的大小。
我强烈推荐阅读Itzik Ben-Gan的“Microsoft SQL Server 2008内幕: T-SQL查询”:
http://www.solidq.com/insidetsql/books/insidetsql2008/
( 2005版也同样适用于此主题)
他探讨了你的问题,以及其他许多人,当涉及到最大限度地利用你的问题。
https://stackoverflow.com/questions/1975623
复制相似问题