Sql-Server

雜湊鍵探測和殘差

  • March 18, 2019

比如說,我們有一個這樣的查詢:

select a.*,b.*
from 
a join b
on a.col1=b.col1
and len(a.col1)=10

假設上述查詢使用 Hash Join 並且有一個殘差,則探測鍵為col1,殘差為len(a.col1)=10

但是在通過另一個範例時,我可以看到探針和殘差都是同一列。以下是我想說的詳細說明:

詢問:

select *
from T1 join T2 on T1.a = T2.a 

執行計劃,探針和殘差突出顯示:

在此處輸入圖像描述

測試數據:

create table T1 (a int, b int, x char(200))
create table T2 (a int, b int, x char(200))

set nocount on
declare @i int
set @i = 0
while @i < 1000
 begin
     insert T1 values (@i * 2, @i * 5, @i)
   set @i = @i + 1
 end

declare @i int
set @i = 0
while @i < 10000
 begin
   insert T2 values (@i * 3, @i * 7, @i)
   set @i = @i + 1
 end

題:

探針和殘差怎麼可能是同一列?為什麼 SQL Server 不能只使用探測列?為什麼它必須使用與殘差相同的列來再次過濾行?

測試數據參考:

tinyint如果連接在鍵入為、smallint或*的單個列上,integer並且如果兩列都被限制NOT NULL為再次設置這些值以確保它們真正匹配。

否則,您將看到殘差,因為雜湊桶中的項目被測試匹配,而不僅僅是雜湊函式匹配。

您的測試沒有指定列NULLNOT NULL列(順便說一句,這是一種不好的做法),因此您似乎正在使用NULL預設的數據庫。

更多資訊在我的文章加入性能、隱式轉換、殘差雜湊加入執行內部,作者是 Dmitry Pilugin。


  • 其他符合條件的類型是bitsmalldatetimesmallmoney和*(var)char(n)*對於 n = 1 和二進制排序規則

引用自:https://dba.stackexchange.com/questions/182917