標籤:style blog http io color os 使用 sp strong
接下來的文章是記錄自己曾經的盲點,同時也透漏了自己的發展曆程(可能發展也算不上,只能說是瞎混)。當然,一些盲點也在工作和探究過程中慢慢有些眉目,現在也願意發揚部落格園的奉獻精神,拿出來和大家分享一下。
開門見上,直接入題
在查看執行計畫時候,你是否曾經也和我一樣,有這樣的疑惑呢?尋找和掃描究竟是什麼,以及他們的在查詢效能上有什麼區別。下面分享下我的理解。
掃描和尋找是SQL Server從表或索引中讀取資料所採用的迭代器,又因為經常在執行計畫中看到,因此理解他們之間的區別,對我們最佳化查詢有很重要的意義。
表掃描是在整張表上進行,而索引掃描是在整個頁級上進行處理的,然而索引尋找則是在尋找謂詞上的一個或者幾個頁上進行,因此他通常情況下,索引尋找會有更少的IO開銷。
由於掃描是對整個表中的行或者頁,不論是否滿足條件,逐一進行的。因此,其查詢開銷是衡定的,與返回結果集無關。索引尋找是在所在謂詞的幾個頁上進行,通常情況下,返回的結果集越多,其開銷就會越大。
然而,通過上面的描述,我們可不能認為,尋找就是好的,而掃描就是不好的(因為影響掃描效能的還有並行度),但是在絕大部分情況下,特別是資料量比較大,而返回的結果集比較少時,尋找要比掃描有著更好的效能表現,另外也不是所有的掃描都可以最佳化掉的。
下面,我們通過例子來認識下,查詢和掃描在效能上的區別。
我們還用SQL Server執行計畫那些事兒(1)中的例子(刪除之前建立的索引)。
我們來執行下面的查詢
1.在沒有索引的情況下
select ID ,Amount,Discount,BuyDate from Headers
select ID ,Amount,Discount,BuyDate from Headers where BuyDate=‘2008-09-15‘
結果:在表掃描的情況下,儘管結果集中,僅一條資料,但是IO開銷並沒有減少,仍然和返回全部結果集是一樣的。
2.在有索引(非叢集索引,要覆蓋返回列,否則會引起RID尋找,或者索引值尋找,這些會在以後的文章中講述。)
建立索引
create nonclustered index index_headers_buyDate on Headers(BuyDate)
include (ID ,Amount,Discount)
go
select ID ,Amount,Discount,BuyDate from Headers
select ID ,Amount,Discount,BuyDate from Headers where BuyDate=‘2008-09-15‘
結果:在索引掃描和索引尋找情況下,所用的開銷和返回的結果緊密相連
總結
1.當表中的資料很少或滿足謂詞的行比較多時,採用掃描操作比較有效。
2.如果表中資料量比較大或滿足謂詞的行較少時,使用掃描將讀取更多的頁面或執行更多的I/O操作來擷取資料,這顯而不是最有效方法.
3.尋找和掃描相比,尋找並不總是好的,掃描也並不是壞的,因為SQL Server可能為該查詢分配多個線程(並行度)。
SQL Server執行計畫那些事兒(2)——尋找和掃描