我有一个启用了 RCSI 的 SQL Server 2016 数据库,它实际上是一堆堆。除了一张表之外,数据库中的所有其他表都是一个堆,最大的堆约为 200GB,占数据库总大小的 50% 以上。
\n\n这个特定的大堆有两个 lob 列,均为 varbinary(max) 数据类型。堆还有许多非聚集索引,幸运的是 varbinary(max) 列不存在于任何这些非聚集索引中,因此它们的大小相对较小。
\n\n供应商提供了一个清理脚本,该脚本从应用程序服务器运行并从这个大堆中清除数据。经过一番调查,我发现此清理脚本不会删除整行,而是根据某些条件将 varbinary(max) 列之一设置为 null。
\n\n以下是有关堆的一些详细信息:
\n\n\n\nSELECT * FROM sys.dm_db_index_physical_stats(DB_ID(N\'<database>\'), OBJECT_ID(N\'GrimHeaper>\'),0, null, \'DETAILED\');\nRun Code Online (Sandbox Code Playgroud)\n\n\n\n\n\nSELECT * FROM sys.dm_db_index_operational_stats(db_id(\'<database>\'),object_id(\'GrimHeaper\'),0,null);\nRun Code Online (Sandbox Code Playgroud)\n\n\n\n\n\n\n\n我对这种情况的理解是,通过将 lob 列中的值设置为 null 释放的空间不会自动重新声明,无论表是堆还是聚集表,都是这种行为,如果我错了,请纠正我。
\n\n在这篇 Microsoft文章以及这篇文章中,它阐述了以下有关索引重组操作的内容:
\n\n\n\n\nREORGANIZE ALL 对所有索引执行 LOB_COMPACTION。对于每个索引,这会压缩聚集索引、基础表中的所有 LOB 列或非聚集索引中包含的列。
\n\n指定 ALL 时,将重新组织与指定表或视图关联的所有索引,并压缩与聚集索引、基础表或包含列的非聚集索引关联的所有 LOB 列。
\n
我觉得这些说法含糊不清,不是很清楚。任何人都可以确认,如果我运行 \xe2\x80\x9cALTER INDEX ALL ON REORGANIZE WITH …