SQL Server 堆heap 非聚集索引 Nonclustered index 行号键查找RID loopup结合执行计划过程详解
SQL Server 堆型數據與執行計劃使用案例
索引的相關術語
1 堆(Heap)是一種沒有指定排序的數據結構,通俗的理解堆就像是按照順序排放的雜物。在數據庫里也即是對應沒有聚集索引。
2 聚集索引:一個表只有一個聚集索引且數據存放在聚集索引內。
3 非聚集索:是一個B-樹(B-Tree)結構,它包含了索引鍵和指向數據行的指針。
我們可以在堆或聚集索引類型的表里創建非聚集索引。一個表的非聚集索引最多支持999個。在覆蓋索引的應用場景下,可以定義非聚集索引時指定包含(include)其它字段。
4 唯一索引:唯一索引不允許表里的指定的列數據有重復的值,一個表可以有一個或多個唯一索引。
5 主鍵:主鍵是一個表里每行記錄的唯一標識同時默認情況下也是聚集索引。
6 RID lookup 堆形式的表的執行計劃里通過ROW id映射匹配其它非聚集索引字段的操作。
堆的演示案例
建立驗證表
借助CTE插入100萬條記錄到EMPLOYEES表。
USE ShenLiang2025 GO CREATE TABLE EMPLOYEES (id INT IDENTITY,name NVARCHAR(50),email NVARCHAR(50),dept NVARCHAR(50) ) GO WITH T AS ( SELECT 1 AS NUM UNION ALL SELECT T.NUM+1 FROM T WHERE T.NUM<1000000 )INSERT INTO EMPLOYEES SELECT 'ABC ' + RTRIM(NUM), 'ABC' + RTRIM(NUM) + '@shenliang2025.COM','dept ' + RTRIM(NUM)FROM T OPTION(MAXRECURSION 0)系統表查看當前表的類型
SELECT * FROM sys.indexes WHERE object_id = OBJECT_ID('dbo.EMPLOYEES')?
無索引下WHERE查詢
--查詢名字是ABC 874000的員工信息。 -- 執行時點擊SSMS里的“包括實際的執行計劃按鈕”菜單(或者用CTRL+M快捷鍵)。 SELECT * FROM EMPLOYEES WHERE NAME = 'ABC 874000'?
通過分析實際的執行計劃不難發現,在堆情況下的表里應用WHERE查詢1條記錄時需要遍歷表里所有的所有記錄(這里是100萬條)。
非聚集索引下WHERE查詢?
--在NAME字段上建立非聚集索引。 CREATE NONCLUSTERED INDEX IX_EMP_NAME ON EMPLOYEES(NAME)-- 再次執行WHERE查詢并含實際執行計劃。 SELECT * FROM EMPLOYEES WHERE NAME = 'ABC 874000'?
?
可見在index seek下讀取的行數和所實際執行的行數都是1,而且估計子樹大小為0.0032831相對于上例的11改進巨大。
RID映射查找?
上例的執行計劃中我們可以看到RID lookup過程,這個映射查找出現的原因是我們的查詢里name字段雖然可以在非聚集索引IX_EMP_NAME上直接獲取到,但id、email、dept而這些信息則需要通過Row ID來映射匹配到。
注:非聚集索引在建立時已經有name字段和Row ID的匹配信息。
RID lookup示意
通過上圖我們可以看到在非聚集索引的葉子節點里存放了索引字段和RID,而通過RID可以找到記錄的所有的字段。?
什么時候用堆類型的表
1 用于插入大量、無序數據的臨時表時。
2 數據量較小時。
3 始終通過非聚集索引訪問數據時。
總結
以上是生活随笔為你收集整理的SQL Server 堆heap 非聚集索引 Nonclustered index 行号键查找RID loopup结合执行计划过程详解的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: win7默认浏览器怎么设置 如何将默认浏
- 下一篇: SQL Server 聚集索引 clus