删除未使用的索引 - 评估意外危险

Ran*_*der 16 index sql-server

根据 DMV 统计数据,我们有一个非常大的数据库,其中包含数百个未使用的索引,这些索引自 7 月份服务器上次重新启动以来一直在累积。我们的一位 DBA 发表了以下警示性声明,这对我来说没有意义:

  1. 在删除索引之前,我们需要确定它是否没有强制执行唯一性约束,因为查询优化器可能需要该索引存在。
  2. 无论何时创建索引,都会在 SQL Server 中创建与该索引相关的统计信息。查询可能没有使用索引,但可能正在使用其统计信息。所以我们可能会遇到这样的情况,在删除索引后,特定的查询性能变得非常糟糕。SQL Server 不保留统计信息的使用情况。尽管我们在数据库上启用了“自动创建统计”功能,但我不知道在查询优化器创建丢失的统计之前必须在内部满足哪些所有参数。

关于#1,在我看来,SQL Server 实际上会在插入/更新完成之前对索引进行查找以确定唯一性,因此,索引不会显示为未使用。

关于#2,这真的可能吗?

顺便说一句,当我说不使用索引时,我的意思是没有搜索和扫描。

Pau*_*ite 18

您的 DBA 的担忧都是有道理的。

关于#1,在我看来,SQL Server 实际上会在插入/更新完成之前对索引进行查找以确定唯一性,因此,索引不会显示为未使用。

优化器可以使用唯一性保证来决定可以使用哪些逻辑转换或物理操作来获得正确的结果。优化器依赖唯一性保证来(例如,转换聚合或选择一对多合并连接)这一事实不会反映在索引使用统计中,除非在最终执行计划中也物理访问该索引. 因此,在删除(或禁用)任何唯一索引或约束时应该非常小心。

关于#2,这真的可能吗?

是的,优化器可以使用与索引相关联的统计信息,而无需使用该索引进行任何访问的最终执行计划。加载“有趣的”统计数据、计算基数估计和生成完成的执行计划的过程是非常独立的活动。

删除索引也会删除关联的索引统计信息,这可能会影响下次重新编译语句时的计划质量。索引统计可用于最终计划所依赖的基数估计计算中,即使该索引实际不存在于最终计划中。

您的 DBA 知道他/她的东西。

这一切都不应被视为意味着永远不应删除明显未使用的索引。我只是说您的 DBA 的担忧是有效的,您应该相应地与他们一起计划更改,通过适当的测试和恢复计划。根据我的经验,第 1 点比第 2 点更有问题,但我无法知道这是否适用于您的情况。