最初,我在 Id 列上创建了一个聚集主键,然后计划创建一个以“Id”作为“索引键列”的非聚集索引,其中“Marks”和“SubmitDate”列将用作“包含列” “在索引中。
我不会这样做的。通过使Id
主键(即唯一)和表的集群键(只有 3 列),添加进一步的 NC 索引没有什么意义Id
- 集群索引就足够了。
如果表中有大量(页上)列,则可能有理由在Id
包含列的情况下添加另一个 NC 索引,(Marks, SubmitDate)
因为 NC 索引密度会更高。但这显然不是这里的情况。
MSDN NC 尺寸链接的一些说明:
- 在树的所有级别中都需要考虑直接索引列。
INCLUDE
列仅存在于树的叶节点中
Num_Key_Cols = Num_Key_Cols + 1
仅当 Sql Server 添加一个4 字节的唯一标识符(如果 Clustering 键不是唯一的)时才需要。您已经按主键进行了聚类,因此它是唯一的,所以不是 +1。
记住也要对真实数据进行经验测量
并非所有表和索引都有固定的列宽 - 许多表和索引都有可变长度的索引列,例如(N)VARCHAR
,在这种情况下,表和索引消耗的实际存储空间高度依赖于这些字段的平均长度。
在这种情况下,我建议创建表并用近似数据填充它,然后使用 和 之类的工具测量实际数据存储sp_spaceused
,sys.dm_db_index_physical_stats
例如:
select * from sys.dm_db_index_physical_stats (DB_ID(),
OBJECT_ID(N'dbo.Table1'), NULL, NULL , 'DETAILED');
(页面大小为 8192)
编辑
只是为了说明,如果你已经有了这个:
CREATE TABLE Table1
(
Id INT IDENTITY(1,1),
Marks INT NOT NULL,
SubmitDate DATE NOT NULL
);
ALTER TABLE Table1 ADD CONSTRAINT PK_Table1 PRIMARY KEY CLUSTERED (Id);
那么这样做也没有意义:
CREATE NONCLUSTERED INDEX IX_Table1 on Table1(Id) INCLUDE (Marks, SubmitDate)
由于聚集索引已经ID
像 NC 索引一样高效地搜索/扫描 - 您只需将存储需求增加一倍。
顺便说一句,还请注意,通常聚集索引键自动包含在所有非聚集索引中,并且不需要显式添加到非聚集索引中。