1. 程式人生 > >SQL Server 索引的自動維護 <第十三篇>

SQL Server 索引的自動維護 <第十三篇>

整理碎片 man 隨著 保存 當前 rebuild int 存儲過程 oca

  在有大量事務的數據庫中,表和索引隨著時間的推移而碎片化。因此,為了增進性能,應該定期檢查表和索引的碎片,並對具有大量碎片的進行整理。

  1、確定當前數據庫中所有需要分析碎片的表。

  2、確定所有表和索引的碎片。

  3、考慮一下因素以確定需要進行碎片整理的表和索引。

  •   高的碎片水平-avg_fragmentation_in_percent大於20%;
  •   不是非常小的表或索引-也就是page_count大於8的;

  4、整理具有大量碎片的表和索引;

  這裏給出一個樣板SQL存儲過程,它執行以下操作;

  •   遍歷系統上的所有數據庫並確認符合碎片條件的每個數據庫中表上的索引,並將它們保存到一個臨時表中;
  •   根據碎片水平,重新整理碎片較少的索引並重建碎片很多的索引。
CREATE PROCEDURE IndexDefrag
AS

DECLARE @DBName NVARCHAR(255)
    ,@TableName NVARCHAR(255)
    ,@SchemaName NVARCHAR(255)
    ,@IndexName NVARCHAR(255)
    ,@PctFrag DECIMAL

DECLARE @Defrag NVARCHAR(MAX)

IF EXISTS (SELECT * FROM sys.objects WHERE
OBJECT_ID = OBJECT_ID(N#Frag)) DROP TABLE #Frag CREATE TABLE #Frag (DBName NVARCHAR(255) ,TableName NVARCHAR(255) ,SchemaName NVARCHAR(255) ,IndexName NVARCHAR(255) ,AvgFragment DECIMAL) EXEC sp_msforeachdb INSERT INTO #Frag ( DBName, TableName, SchemaName, IndexName, AvgFragment ) SELECT
‘‘?‘‘ AS DBName ,t.Name AS TableName ,sc.Name AS SchemaName ,i.name AS IndexName ,s.avg_fragmentation_in_percent FROM ?.sys.dm_db_index_physical_stats(DB_ID(‘‘?‘‘), NULL, NULL, NULL, ‘‘Sampled‘‘) AS s JOIN ?.sys.indexes i ON s.Object_Id = i.Object_id AND s.Index_id = i.Index_id JOIN ?.sys.tables t ON i.Object_id = t.Object_Id JOIN ?.sys.schemas sc ON t.schema_id = sc.SCHEMA_ID WHERE s.avg_fragmentation_in_percent > 20 AND t.TYPE = ‘‘U‘‘ AND s.page_count > 8 ORDER BY TableName,IndexName DECLARE cList CURSOR FOR SELECT * FROM #Frag OPEN cList FETCH NEXT FROM cList INTO @DBName, @TableName,@SchemaName,@IndexName,@PctFrag WHILE @@FETCH_STATUS = 0 BEGIN IF @PctFrag BETWEEN 20.0 AND 40.0 BEGIN SET @Defrag = NALTER INDEX + @IndexName + ON + @DBName + . + @SchemaName + . + @TableName + REORGANIZE EXEC sp_executesql @Defrag PRINT Reorganize index: + @DBName + . + @SchemaName + . + @TableName +. + @IndexName END ELSE IF @PctFrag > 40.0 BEGIN SET @Defrag = NALTER INDEX + @IndexName + ON + @DBName + . + @SchemaName + . + @TableName + REBUILD EXEC sp_executesql @Defrag PRINT Rebuild index: + @DBName + . + @SchemaName + . + @TableName +. + @IndexName END FETCH NEXT FROM cList INTO @DBName, @TableName,@SchemaName,@IndexName,@PctFrag END CLOSE cList DEALLOCATE cList DROP TABLE #Frag

SQL Server 索引的自動維護 <第十三篇>