为什么在独特的非聚集索引根页面中没有堆存在,而是存在于非唯一非聚簇索引的根页面中?

问题描述:

我正在做一些分析并试图了解SQL Server 2008上的唯一和非唯一非聚集索引?在技​​术博客之后,我做了以下工作。为什么在独特的非聚集索引根页面中没有堆存在,而是存在于非唯一非聚簇索引的根页面中?

 USE TEST 
    CREATE TABLE "CustomersHeap" (
     "CustomerId" INT NOT NULL, 
     "CustomerName" CHAR(100) NOT NULL, 
     "CustomerAddress" CHAR(100) NOT NULL, 
     "Comments" CHAR(189) NOT NULL 
    ) 
    ; 


    USE TEST 
    DECLARE @i INT = 1 WHILE (@i <= 80000) BEGIN 
    INSERT INTO dbo.CustomersHeap VALUES 
    (
    @i, 
    'CustomerName' + CAST(@i AS CHAR), 
    'CustomerAddress' + CAST(@i AS CHAR), 
    'Comments' + CAST(@i AS CHAR) 
    ) SET @i += 1 
    END 

    -- Create a unique non clustered index 
    CREATE UNIQUE NONCLUSTERED INDEX IDX_UniqueNCI_CustomerID 
    ON Test.dbo.CustomersHeap(CustomerId) 


    -- Create a non-unique non clustered index 
    CREATE NONCLUSTERED INDEX IDX_NonUniqueNCI_CustomerID 
    ON Test.dbo.CustomersHeap(CustomerId) 

    --Get indexes 
    select * from sys.indexes where object_id=OBJECT_ID('Test.dbo.CustomersHeap') 


    --After figuring out index and child pages using DBCC IND 
    DBCC TRACEON(3604) 
    --UniqueNonClusteredIndex root page 
    DBCC PAGE(Test, 1, 4160, 3) 
    --NonUniqueNonClusteredIndex root page 
    DBCC PAGE(Test, 1, 4416, 3) 

第一页的输出语句中不包含一个名为“堆RID”,其中的第二页声明的输出确实列。我无法理解为什么?特别是当所有行都有ChildPageId的信息并且它们应该正确地包含“HEAP RID”时。

此附加列增加了非唯一非聚集索引的根页面的大小。

第一页声明 输出列的fileid,的PageId,行,等级,ChildFileId,ChildPageId,客户ID,KeyHashValue

的第二页的声明 输出列的fileid,的PageId,行,等级,ChildFileId,ChildPageId,客户ID ,HEAP RID,KeyHashValue

+0

我对此的理解是非常不完整的,但我的猜测是Hep RID可能被添加到非唯一索引中,使其(或者说,其中的键)在内部是唯一的? – stakx

+1

也就是说,在唯一索引的情况下,SQL Server知道'CustomerId'本身就足以找到具有完整数据的特定表行。在非唯一索引的情况下,原始表中可能有多行具有相同的'CustomerId',因此SQL Server通过添加内部(和唯一)RID来使索引中的“外键”唯一。通过将索引键转换为复合键。 – stakx

请仔细阅读这些文章(包括克劳斯Aschenbrenner书面):

摘录:

“这里的结论是,在非唯一聚集索引的唯一非聚集索引仅让4字节的开销在叶聚集索引的级别,因为这里SQL Server直接指向正确的记录。有参与了独特的非聚集索引的非叶水平没有额外的开销。”

,因为它直接指向正确的记录,没有堆RID。

由于独特的关键是本身是行的唯一标识符,在唯一配置项或唯一NCI中没有RID,当该行中没有唯一密钥时会发生RID,因此SQL Server会添加行标识符(RID)来定位行并爬上B-tree

所以RID与CI或NCI无关RID与行的唯一性有关

+0

@ KumarHarsh-这两个博客都是由同一个人编写的。这里的问题只是与根级索引页面有关而不是叶级别页面。它对根页面的诊断我有疑问。 – 100pipers

+0

@ 100pipers,查看我的最后一段。 – KumarHarsh

+0

@ kumarharsh-那么,我们说,由于非唯一的非聚集索引可以有100项与同一ID说一句,为了区分这些1S,SQL服务器附加一个摆脱?谢谢。 – 100pipers