為什麼 sql server 更喜歡非聚集索引而不是聚集索引?
我正在嘗試加快桌子的速度,並且在進行試驗時遇到了這個(我認為是)奇怪的情況。我創建了一個應該是同一個東西的聚集索引和非聚集索引。但是,當我對錶執行查詢時,我發現 SQL Server 總是希望使用非聚集索引而不是匹配的聚集索引。最重要的是,當需要時,SQL Server 將正確地對非聚集索引進行索引搜尋,但總是對聚集索引執行掃描。
為什麼 SQL Server 更喜歡非聚集索引?
我怎樣才能重寫這個,所以我仍然有性能提升,但只有聚集索引?
我有以下表結構:
CREATE TABLE [dbo].[Variables]( [ID] [bigint] IDENTITY(1,1) NOT NULL, [Header] [varchar](255) NULL, [FullVariables] [varchar](max) NULL )
聚集索引:
ALTER TABLE [dbo].[Variables] ADD CONSTRAINT [PK_Variables] PRIMARY KEY CLUSTERED ( [ID] ASC )
非聚集索引:
CREATE UNIQUE NONCLUSTERED INDEX [NonClusteredIndex-20190307-091011] ON [dbo].[Variables] ( [ID] ASC ) INCLUDE ( [Header], [FullVariables])
我目前的知識使我相信,在這種情況下,這兩個索引都應該包含以相同方式排列的數據
$$ ID $$作為關鍵列,然後$$ Header $$和$$ FullVariables $$作為索引中包含的額外數據,而不是指針。如果您有一些可以連結的知識來源,我非常渴望閱讀更多內容。 我應該指定我並不總是想要搜尋,並且我知道在某些情況下掃描會更好(否則為什麼會有它)。由於行大小(數百萬)乘以
varchar(MAX)
(包含 16000 多個字元長的字元串),該表包含大約 60GB 的數據。在插入表之前,會進行掃描以確保沒有插入重複項(匹配 onHeader
用於消除和 onFullVariables
)。然後在需要查找的 ID 欄位上將表連接到幾個視圖中。
如果 SQL Server 有兩個索引可供選擇,這兩個索引都滿足(“覆蓋”)查詢並提供定位和/或排序行的最佳路徑,則應將其視為拋硬幣。不過,這不是……我相信這裡(可能是我,這里和這裡)進行了一些研究,表明它選擇了最近創建的一個或按字母順序排列的第一個或其他任意的東西。
但是,如果我們稱之為硬幣翻轉涉及在非聚集索引和聚集索引之間進行選擇,並且兩個索引都正確滿足查詢,SQL Server 將始終傾向於非聚集索引。為什麼?因為它保證不會比聚集索引*更寬。*不考慮與聚集索引的寬度完全相同的邊緣情況。
您應該查看每個執行計劃所涉及的成本,並確認 SQL Server 估計的非聚集索引的成本 <= 聚集索引的成本。如果您可以舉一個反例,即選擇非聚集索引,即使其估計成本高於聚集索引,請這樣做。