clo*_*afe 5 sql-server indexing sql-server-2012
我们在uniqueidentifier上设计了一个设计不佳的索引.我们在我们的系统上找不到任何会导致使用它的查询,但这并不意味着连接应用程序肯定不需要它.
该表具有超过6亿行,其聚簇索引不是唯一的.每个聚簇索引值重复超过100万次.由于表的大小,我们很难删除索引,因为很难重新创建它.没有钥匙.
在dm_db_index_usage_stats中没有针对它的扫描或查找,但是dm_db_index_usage_stats确实显示少量针对它的查找.
我们已经搜索了查询计划,并且只查找了作为更大的聚簇索引更新的一部分被引用的时间; 没有明确的索引寻求.
它们是作为统计更新的一部分,索引更新的一部分完成的,还是查询引擎可能在更深层次的自联接计算中使用它,因为它是表中唯一的唯一字段?
如果有人可以解释搜索,我们可能会放弃它并获得性能提升.
SQL Server 索引本质上是表中已存在的数据的副本,以不同的方式排序和过滤,以提高执行查询的性能。查找、扫描和查找运算符用于访问 SQL Server 索引。
\n\n查找运算符\xe2\x80\x93 查找运算符使用 SQL Server 搜索索引的功能,从聚集或非聚集索引中获取行,查找可以是物理运算符,也可以是逻辑运算符。索引查找仅处理合格的行和包含这些合格行的页,因此查找的成本较低。简而言之,试图从表中检索选定的行。
\n\nScans 运算符\xe2\x80\x93 Scans 运算符扫描聚集索引,它旨在处理扫描表中的每一行,无论该行是否合格。扫描运算符对于小型表或大多数行都是合格的情况可能很有效。简单来说,扫描检索表中的所有行。
\n\n查找运算符\xe2\x80\x93 查找运算符,用于从非聚集索引检索的结果集中检索非键数据。从非聚集索引检索行后,将使用查找从这些行中检索列信息。
\n\n虽然正确使用 SQL Server 索引可以提高执行查询的性能,但一般而言,如果 SQL Server 设置不当或未在需要的地方设置它们,可能会显着降低执行查询的性能。此外,拥有查询未使用的不必要的索引也可能会出现问题。
\n\nSQL Server 索引是提高 SELECT 查询性能的绝佳工具,但同时 SQL Server 索引对数据更新也有负面影响。INSERT、UPDATE 和 DELETE 操作会导致索引更新,从而复制表中已存在的数据。因此,这会增加事务和查询执行的持续时间,并且通常会导致锁定、阻塞、死锁和相当频繁的执行超时。对于大型数据库或表,存储空间也会受到冗余索引的影响。任何 SQL Server DBA 的一个关键目标是维护索引,包括创建所需的索引,但同时删除未使用的索引。
\n\n查找未使用的索引
\n\nSQL Server 通过动态管理视图 (DMV) 提供大量索引信息。dm_db_index_usage_stats DMV 显示有关索引使用情况的基本信息,它是识别未使用的 SQL Server 索引的有用工具。当第一次使用索引时,DMV 中会创建一个新行dm_db_index_usage_stats,并随后在每次使用索引时进行更新。但是,与每个 DMV 一样,dm_db_index_usage_stats 中的数据仅包含自上次 SQL Server 服务重新启动以来的数据(SQL Server 服务重新启动会重置 DMV 中的数据)。因此,自上次 SQL Server 重新启动以来有足够的时间来正确确定哪些索引适合删除是至关重要的。
可用于获取 SQL Server 中未使用索引(在任何查找、扫描或查找操作中未使用的更新索引)列表的简单查询如下:
\n\nSELECT\n objects.name AS Table_name,\n indexes.name AS Index_name,\n dm_db_index_usage_stats.user_seeks,\n dm_db_index_usage_stats.user_scans,\n dm_db_index_usage_stats.user_updates\nFROM\n sys.dm_db_index_usage_stats\n INNER JOIN sys.objects ON dm_db_index_usage_stats.OBJECT_ID = objects.OBJECT_ID\n INNER JOIN sys.indexes ON indexes.index_id = dm_db_index_usage_stats.index_id AND dm_db_index_usage_stats.OBJECT_ID = indexes.OBJECT_ID\nWHERE\n AND\n dm_db_index_usage_stats.user_lookups = 0\n AND\n dm_db_index_usage_stats.user_seeks = 0\n AND\n dm_db_index_usage_stats.user_scans = 0\nORDER BY\n dm_db_index_usage_stats.user_updates DESC\nRun Code Online (Sandbox Code Playgroud)\n\n上面的查询返回所有类型的所有未使用的索引。此查询经常可以在互联网上找到,但\xe2\x80\x99并不是一个理想/完整的选项。通过使用此类查询来查找和清理未使用的索引可能会导致意外行为,因为此查询在收集未使用的索引数据时不考虑主键和唯一键约束。主键约束索引和唯一键约束索引都可以是 \xe2\x80\x9cunused、\xe2\x80\x9d,但删除这些索引可能会出现问题。为了防止出现这种情况,必须通过在 WHERE 之后添加两行代码来优化上面的查询,以排除主键和唯一键被列为未使用和可能被删除的情况。
\n\nSELECT\n objects.name AS Table_name,\n indexes.name AS Index_name,\n dm_db_index_usage_stats.user_seeks,\n dm_db_index_usage_stats.user_scans,\n dm_db_index_usage_stats.user_updates\nFROM\n sys.dm_db_index_usage_stats\n INNER JOIN sys.objects ON dm_db_index_usage_stats.OBJECT_ID = objects.OBJECT_ID\n INNER JOIN sys.indexes ON indexes.index_id = dm_db_index_usage_stats.index_id AND dm_db_index_usage_stats.OBJECT_ID = indexes.OBJECT_ID\nWHERE\n indexes.is_primary_key = 0 -- This condition excludes primary key constarint\n AND\n indexes. is_unique = 0 -- This condition excludes unique key constarint\n AND\n dm_db_index_usage_stats. user_lookups = 0\n AND\n dm_db_index_usage_stats.user_seeks = 0\n AND\n dm_db_index_usage_stats.user_scans = 0\nORDER BY\n dm_db_index_usage_stats.user_updates DESC\nRun Code Online (Sandbox Code Playgroud)\n\n上面的查询列出了所有未使用的非主键和唯一键的查询,但它还列出了 SQL Server 尚未使用的所有未使用的索引。dm_db_index_usage_stats DMV 中的 user_updates 列正在计算索引更新的位置,因为应用程序对数据进行了一些更改,因此索引已更新。为此,dm_db_index_usage_stats.user_updates <> 0应将条件添加到先前的脚本中。
SELECT\n objects.name AS Table_name,\n indexes.name AS Index_name,\n dm_db_index_usage_stats.user_seeks,\n dm_db_index_usage_stats.user_scans,\n dm_db_index_usage_stats.user_updates\nFROM\n sys.dm_db_index_usage_stats\n INNER JOIN sys.objects ON dm_db_index_usage_stats.OBJECT_ID = objects.OBJECT_ID\n INNER JOIN sys.indexes ON indexes.index_id = dm_db_index_usage_stats.index_id AND dm_db_index_usage_stats.OBJECT_ID = indexes.OBJECT_ID\nWHERE\n indexes.is_primary_key = 0 --This line excludes primary key constarint\n AND\n indexes. is_unique = 0 --This line excludes unique key constarint\n AND \n dm_db_index_usage_stats.user_updates <> 0 -- This line excludes indexes SQL Server hasn\xe2\x80\x99t done any work with\n AND\n dm_db_index_usage_stats. user_lookups = 0\n AND\n dm_db_index_usage_stats.user_seeks = 0\n AND\n dm_db_index_usage_stats.user_scans = 0\nORDER BY\n dm_db_index_usage_stats.user_updates DESC\nRun Code Online (Sandbox Code Playgroud)\n\n因此,既然已识别并列出了未使用的 SQL Server 索引,就可以确定哪些索引可以安全删除,但同样必须非常小心地进行。
\n| 归档时间: |
|
| 查看次数: |
254 次 |
| 最近记录: |