
























本文对SQLServer中的索引进行一个知识总结。
未创建聚集索引的表称为堆表,数据无序追加,无统一排序。
-- 创建堆表(无聚集索引)
CREATE TABLE TestData (
TestId integer, TestName varchar(255), TestDate date,
TestType integer, TestData1 integer, TestData2 varchar(100),
TestData3 XML, TestData4 varbinary(max), TestData4_FileType varchar(3)
);
ALTER TABLE TestData REBUILD; -- 重建堆表
DROP TABLE TestData; -- 删除表
B+树结构,索引键与完整行数据存储在叶子节点。一张表最多1个聚集索引,创建后不再为堆表。
CREATE CLUSTERED INDEX IX_TestData_TestId ON dbo.TestData (TestId);
ALTER INDEX IX_TestData_TestId ON TestData REBUILD WITH (ONLINE = ON); -- 在线重建
DROP INDEX IX_TestData_TestId ON TestData WITH (ONLINE = ON); -- 在线删除
B+树结构,叶子节点不存完整行,仅存行定位指针(指向聚集索引键或堆表的RID)。
CREATE INDEX IX_TestData_TestDate ON dbo.TestData (TestDate);
ALTER INDEX IX_TestData_TestDate ON TestData REBUILD WITH (ONLINE = ON);
DROP INDEX IX_TestData_TestDate ON TestData;
按列存储的特殊索引,分为聚集列存储与非聚集列存储两种。
-- 创建聚集列存储索引
CREATE CLUSTERED COLUMNSTORE INDEX CIX_TestData_TestType ON dbo.TestData (TestType)
WITH (DATA_COMPRESSION = COLUMNSTORE);
DROP INDEX CIX_TestData_TestType;
专用于 XML 类型字段,分为主XML索引和二级XML索引(PATH/VALUE/PROPERTY),前置要求:表必须有主键聚集索引。
CREATE PRIMARY XML INDEX PXML_TestData_TestData3 ON TestData (TestData3);
CREATE XML INDEX XMLPATH_TestData_TestData3 ON TestData (TestData3)
USING XML INDEX PXML_TestData_TestData3 FOR PATH;
CREATE XML INDEX XMLPROPERTY_TestData_TestData3 ON TestData (TestData3)
USING XML INDEX PXML_TestData_TestData3 FOR PROPERTY;
CREATE XML INDEX XMLVALUE_TestData_TestData3 ON TestData (TestData3)
USING XML INDEX PXML_TestData_TestData3 FOR VALUE;
将文本拆分为分词(Token)构建索引,索引文件独立存放于全文目录,不混存于数据文件。
CREATE FULLTEXT CATALOG fulltextCatalog AS DEFAULT;
CREATE FULLTEXT INDEX ON dbo.TestData (TestData4 TYPE COLUMN TestData4_FileType)
KEY INDEX PK_TestData WITH STOPLIST = SYSTEM;
ALTER FULLTEXT CATALOG fulltextCatalog REBUILD;
DROP FULLTEXT INDEX ON dbo.TestData;
非聚集索引扩展:将指定字段存入叶子节点,实现"类聚集索引"效果,免去回表。支持 text/ntext/image 外的绝大多数类型。
CREATE NONCLUSTERED INDEX IX_TestData_TestDate_incTestData3 ON TestData (TestDate)
INCLUDE (TestData3);
SQL Server 不直接支持函数索引,通过持久化计算列模拟实现。
ALTER TABLE TestData ADD TestDatePlus7Days AS DATEADD(DAY, 7, TestDate) PERSISTED;
CREATE NONCLUSTERED INDEX IX_TestData_TestDate_Plus7Days ON TestData (TestDatePlus7Days);
带 WHERE 条件的非聚集索引,缩小索引体积、降低维护成本。仅当查询条件与索引 WHERE 完全匹配时优化器才会选用。
CREATE INDEX IX_TestData_TestDate_TestTypeEq1 ON TestData (TestDate) WHERE TestType = 1;
设计思路:查询所有字段要么是索引键,要么在 INCLUDE 中,完全消除回表,性能最优。
CREATE INDEX IX_TestData_TestDate_TestType_AllData ON TestData (TestDate, TestType)
INCLUDE (TestData1, TestData2, TestData3, TestData4);
-- 该查询完全走索引,无需访问原表
SELECT TestData1, TestData2, TestData3, TestData4
FROM TestData
WHERE TestDate > CURRENT_TIMESTAMP - 1 AND TestType = 1;
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。