Quando devono essere eliminati e ricreati gli indici?


9

Stiamo costruendo un data warehouse che inizialmente sarà di 1 TB e crescerà di circa 20 grammi al mese.

Per alcune tabelle stiamo eseguendo processi ETL giornalieri e altri stiamo facendo settimanalmente / mensilmente.

Quando è presente un'importazione di dati in una tabella, è necessario eliminare e ricreare gli indici?

Esiste mai un punto per eliminare e ricreare gli indici o vengono aggiornati automaticamente?

Le statistiche sono impostate per l'aggiornamento automatico.

Grazie mille per l'aiuto e la guida.

Ho ottenuto questo copione geniale:

SELECT 'ALTER INDEX [' + ix.name + '] ON [' + s.name + '].[' + t.name + '] ' +
       CASE WHEN ps.avg_fragmentation_in_percent > 40 THEN 'REBUILD' ELSE 'REORGANIZE' END +
       CASE WHEN pc.partition_count > 1 THEN ' PARTITION = ' + cast(ps.partition_number as nvarchar(max)) ELSE '' END
FROM   sys.indexes AS ix INNER JOIN sys.tables t
           ON t.object_id = ix.object_id
       INNER JOIN sys.schemas s
           ON t.schema_id = s.schema_id
       INNER JOIN (SELECT object_id, index_id, avg_fragmentation_in_percent, partition_number
                   FROM sys.dm_db_index_physical_stats (DB_ID(), NULL, NULL, NULL, NULL)) ps
           ON t.object_id = ps.object_id AND ix.index_id = ps.index_id
       INNER JOIN (SELECT object_id, index_id, COUNT(DISTINCT partition_number) AS partition_count
                   FROM sys.partitions
                   GROUP BY object_id, index_id) pc
           ON t.object_id = pc.object_id AND ix.index_id = pc.index_id
WHERE  ps.avg_fragmentation_in_percent > 10 AND
       ix.name IS NOT NULL

da qui:

http://weblogs.asp.net/okloeten/archive/2009/01/05/6819737.aspx

Mi suggerisce di eseguire questo script quotidianamente e in base ai risultati eseguo il codice generato?


ti sarei molto grato se qualcuno mi spiegasse qual è il problema con la mia domanda
l

Ecco una domanda correlata che ho posto. dba.stackexchange.com/questions/11389/… Le conoscenze che ho acquisito da questa domanda e le risposte mi hanno insegnato molto e grazie a ciò abbiamo realizzato grandi guadagni.
Scambia il

Risposte:


13

Se si tratta di ETL ciclico e ci si trova in un ambiente di dati di sviluppo (ovvero NON LIVE), è necessario gestire gli indici come parte del ciclo di carico.

Lo faccio per diversi set di dati ogni mese, il più grande dei quali aggiunge circa 100 GB mensili a un set di dati da 5 TB.

Ho effettuato test approfonditi e, per esperienza personale, il modo più efficiente di caricare gli indici è:

  1. DISABLE indici non cluster, lasciando intatto l'indice cluster
  2. Esegui il caricamento di raw nella tabella dei dati
  3. REBUILD Indici NC

Se aggiungi periodicamente solo righe come parte dell'ETL gestito, questa è la strada da percorrere. Questo assicura anche che tutte le tue statistiche siano aggiornate.

Per le statistiche, è importante notare che l'aggiunta di 20 GB a un database da 1 TB non raggiungerà il punto di non ritorno per un aggiornamento automatico delle statistiche, quindi è possibile aggiungere un intero mese di dati senza mai aggiornare le statistiche.

Ricostruire gli indici NC è un buon modo per aggirare questo. È possibile che si desideri eseguire periodicamente anche la ricostruzione di un indice cluster se la frammentazione aumenta (a seconda della struttura della tabella e della chiave cluster).


4
Puoi anche aggiornare le statistiche come parte separata del tuo processo, mescolate tra ricostruzioni NC se farlo spesso è troppo costoso.
Aaron Bertrand

1

Per un database da 1 TB +, l'eliminazione e la creazione giornaliera di indici sarebbe eccessiva (anche se si ricrea solo alcuni di essi).

Se sei preoccupato per le velocità di inserimento / aggiornamento nella tua tabella a causa del sovraccarico aggiunto dagli aggiornamenti dell'indice, allora ti consiglio due cose:

  1. Utilizzare PK surrogati in modo che gli inserimenti di indice cluster abbiano un sovraccarico minimo.
  2. Crea il profilo del tuo DWH e crea indici non cluster dove assolutamente necessario.

Dovrai convivere con gli aggiornamenti dell'indice non cluster durante le operazioni di inserimento / aggiornamento.

Se sei preoccupato per la frammentazione dell'indice, ti consiglio di creare lavori quotidiani (lavori di SQL Agent) per ricostruire gli indici. Il periodo di ricostruzione può effettivamente essere qualsiasi cosa, dipende dal livello di frammentazione. Si dovrebbe notare questo in pratica e impostare di conseguenza la pianificazione del lavoro.

È possibile aggiungere un po 'di logica agli script di ricostruzione, a seconda del livello di frammentazione. Alcune buone linee guida che puoi trovare qui .

La linea di fondo è che in ogni caso non si dovrebbe fare una ricostruzione dell'indice completo su un database di quelle dimensioni.


6
Non sono d'accordo con molto di questo. Dipenderà dal suo caso d'uso, ma quest'ultima riga under any circumstances you shouldn't do a full index rebuild on a database of that size.non è affatto precisa. Faccio ETL su database di grandi dimensioni come compito principale e vedo enormi benefici dalla disabilitazione e ricostruzione degli indici.
JNK,

1
Vorrei che questo fosse applicato anche nel mio caso. Su un database leggermente superiore a 1 TB in esecuzione su un ambiente di produzione, riesco a malapena a fare una ricostruzione di un indice non cluster notturno per più tabelle con oltre 500 milioni. filari. Ho diversi processi ETL in esecuzione ogni notte e l'ultimo passo che faccio dalle 3:00 del mattino è ricostruire gli indici.
Marcel N.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.