何时应该重建关系数据库( Server)中的索引?
是否有理由定期重建索引?
发布于 2011-08-03 19:31:29
尽管我的回答过于笼统,但我会说,您应该定期运行索引维护过程。但是,您的索引维护过程只应该重建/重新组织特定需要它的索引。
这就提出了一个问题:何时需要重建或重新组织索引?罗兰多很好地触及了这个问题。再说一次,我冒着极其宽泛的风险。当碎片级别对性能产生不利影响时,索引需要维护。这种分割程度可能因索引的大小和组成而有所不同。
就Server而言,我倾向于选择索引大小和索引分段级别,在此开始执行索引维护。如果索引包含的页面少于100页,我将不执行维护。
如果一个索引在10%到30%之间支离破碎,我将REORGANIZE索引和UPDATE统计。如果一个索引超过30%的碎片,我将REBUILD索引-没有UPDATE STATISTICS,因为这是由REBUILD处理。不过,请记住,重构只更新与索引直接关联的statistics对象。其他列统计数据需要单独维护。
这个答案实际上只是说了很长一段路:是的,您应该做常规的索引维护,但是只对需要它的索引进行维护。
发布于 2011-08-04 05:56:04
何时应该重建关系数据库中的索引(例如Server)?
当索引被特殊事件严重分割时,您应该重新构建它们。例如,将大量数据大容量加载到索引表中。
是否有理由定期重建索引?
那么,如果您的索引由于有规律的活动而定期变得支离破碎怎么办?你应该定期重新构建吗?他们应该多久跑一次?
汤姆·凯特,在这个经典的问汤姆线中,建议:
索引重建之间的时间间隔应该是大约永远的。..。不知道怎么说得更好--指数想要更大更胖,有更多的空间。它位于您更新的列上--将索引条目从一个地方移到另一个地方。第一天行的代码是"A",第二天的代码是"G",然后是"Z“然后是"H”等等。因此,行的索引条目在索引中从一个地方移动到另一个地方。当它这样做的时候,它需要空间--如果空间不存在,我们将块分割成2的空间。现在指数变胖了。随着时间的推移,索引的大小是开始时的2-3倍,并且是“一半或更多的空”,但这是可以的,因为您可以左右移动行。现在,当我们左右移动的时候,我们不再需要分割块来腾出空间--这个房间已经可用了。然后你来重建或删除并重新创建索引(它具有相同的效果--只是重建更安全-没有丢失索引的机会,而且可以更快,因为可以通过扫描现有索引来重建索引,而不是扫描表、排序和构建一个新的索引)。现在,所有美好的空间都消失了。我们重新开始了分块的过程--让我们回到我们开始的地方。你没有节省任何空间。指数正好回到了原来的水平。你将只是在浪费你的时间来再次重建它,导致这种恶性循环重演。
这里的逻辑是合理的,但它偏袒一个读重的负载配置文件。
一个"fat“索引(即一个有很多空白的索引)确实为新行和移动行保留了很大的空间,从而减少了页面分割并保持了您的书写速度。但是,当您从胖索引中读取数据时,您必须阅读更多的页面才能获得相同的数据,因为您现在正在筛选更多的空白空间。这减慢了你的阅读速度。
因此,在读量大的数据库中,您希望定期重新构建或重新组织索引。(多久一次,在什么条件下?Matt已经有一个具体答案来回答这个问题。)在经历大致相等的读和写活动的数据库中,或者在写量大的数据库中,您可能会通过定期重新生成索引来损害数据库的性能。
发布于 2017-12-14 21:13:30
正如Matt所接受的答案所指出的,一个常见的经验法则是,超过30%的零碎索引应该重建。
这个查询将帮助您找到有多少个索引碎片超过30% (当您有一些索引时,您应该重新构建它们):
SELECT DB_NAME() AS DBName,
OBJECT_NAME(ind.object_id) AS TableName,
ind.name AS IndexName,
indexstats.index_type_desc AS IndexType,
indexstats.avg_fragmentation_in_percent,
indexstats.fragment_count,
indexstats.avg_fragment_size_in_pages,
SUM(p.rows) AS Rows
FROM sys.dm_db_index_physical_stats(DB_ID(), NULL, NULL, NULL, NULL) AS indexstats
INNER JOIN sys.indexes AS ind ON ( ind.object_id = indexstats.object_id
AND ind.index_id = indexstats.index_id)
INNER JOIN sys.partitions AS p ON ( ind.object_id = p.object_id
AND ind.index_id = p.index_id)
WHERE indexstats.avg_fragmentation_in_percent > 30
GROUP BY
OBJECT_NAME(ind.object_id),
ind.name,
indexstats.index_type_desc,
indexstats.avg_fragmentation_in_percent,
indexstats.fragment_count,
indexstats.avg_fragment_size_in_pages
ORDER BY indexstats.avg_fragmentation_in_percent DESChttps://dba.stackexchange.com/questions/4283
复制相似问题