[SQL SERVER][Performance]密度和選擇性

[SQL SERVER][Performance]密度和選擇性

3月份SQL PASS TW活動我有介紹密度和選擇性關係,

統計值透過密度比率來判斷索引欄位選擇性高低,

換句話說,索引有效性取決於統計值,統計值影響執行計畫好壞,

所以統計值在資料庫扮演相當重要的角色。

一般來說低密度索引欄位表示高選擇性(密度越低越適合nonclustered index key),

高選擇性可以幫助查詢優化程式在大資料量中快速搜尋小結果集,

查詢調校過程中,大部分時間會花在索引優化上,

這裡我大概分享一下自己如何確認索引有效性。

 

相信大家都有聽說過,index key順序會引響效能,

主要是因為統計值所造成,下面是當天活動demo script,

大家可以猜猜看,SQL SERVER查詢優化程式會決定走那一個索引。

 

--#密度和選擇性
select Rate,PayFrequency,ModifiedDate
from EmployeePayHistory  
where PayFrequency=2
and ModifiedDate between '2004-07-31' and '2004-08-10'

	
drop index idx1 on EmployeePayHistory 
create index idx1 on EmployeePayHistory(PayFrequency,ModifiedDate)
include(Rate) 

	
drop index idx2 on EmployeePayHistory 
create index idx2 on EmployeePayHistory(ModifiedDate,PayFrequency)  
include(Rate) 

	
dbcc show_statistics(EmployeePayHistory,idx1)
dbcc show_statistics(EmployeePayHistory,idx2)

 

idx1統計值(擷取部分)

 

 

image

PayFrequency 密度0.5

 

 

idx2統計值(擷取部分)

image

ModifiedDate 密度 0.03846154

 

前面我有說過低密度高選擇性,所以你可能會直覺認定查詢最佳化程式會走idx2 索引,

很不幸你不能只單單做這樣的判斷,因為選擇性主要是因你查詢條件資料分布所決定,

這裡我有一個估算方法。

 

 

ModifiedDate between '2004-07-31' and '2004-08-10' 資料分布

image

 

符合ModifiedDate 條件資料分布有 277,該索引總筆數 316,所以密度 select (1.0*277)/316

image

 

 

PayFrequency=2 資料分布

image

 

符合PayFrequency=2條件資料分布有 136,該索引總筆數 316,所以密度 select (1.0*136)/316

image

 

兩個索引密度都算出來,套用之前我所說的,

低密度高選擇性,高選擇性越適合成為nonclustered index key,

所以這次查詢優化程式會使用訪問索引 idx1。

image

確實使用索引idx1。

 

當然對於索引優化這只是一小部分,

未來如有機會希望可以和大家分享不求人系列二--索引優化不求人  微笑