Da MSDN :
"Le operazioni di inserimento si verificano su colonne chiave
crescente o decrescente Le statistiche su colonne chiave crescente o decrescente, come le colonne IDENTITY o timestamp in tempo reale, potrebbero richiedere aggiornamenti statistici più frequenti rispetto a Query Optimizer. Le operazioni di inserimento aggiungono nuovi valori a colonne ascendenti o discendenti Il numero di righe aggiunte potrebbe essere troppo piccolo per attivare un aggiornamento delle statistiche Se le statistiche non sono aggiornate e le query selezionano dalle righe aggiunte più di recente, le statistiche correnti non avranno stime di cardinalità per questi nuovi valori. risulta in stime di cardinalità inaccurate e prestazioni lente delle query.
Ad esempio, una query che seleziona tra le date dell'ordine di vendita più recenti avrà stime di cardinalità inaccurate se le statistiche non vengono aggiornate per includere le stime di cardinalità per le date dell'ordine di vendita più recenti.
Dopo le operazioni di manutenzione
Considerare l'aggiornamento delle statistiche dopo aver eseguito le procedure di manutenzione che modificano la distribuzione dei dati, come il troncamento di una tabella o l'esecuzione di un inserimento in blocco di una grande percentuale delle righe. Ciò può evitare ritardi futuri nell'elaborazione delle query mentre le query attendono aggiornamenti automatici delle statistiche ".
È possibile utilizzare "EXEC sp_updatestats" di volta in volta sul proprio sistema (programmato di volta in volta) o utilizzare la funzione STATS_DATE su tutti gli oggetti e vedere quando le loro statistiche sono state effettivamente aggiornate l'ultima volta e se da allora è trascorso troppo tempo, utilizzare UPDATE STATISTICHE per quel particolare oggetto. Nella mia esperienza, anche con le statistiche automatiche abilitate, siamo comunque costretti ad aggiornare le statistiche di tanto in tanto, a causa delle operazioni di inserimento che non hanno attivato l'aggiornamento automatico.
Per aggiungere il mio codice personale (utilizzato in un lavoro settimanale che crea dichiarazioni dinamiche per l'aggiornamento delle statistiche):
select distinct
'update statistics [' + stats.SchemaName + '].[' + stats.TableName + ']'
+ case when stats.RowCnt > 50000 then ' with sample 30 percent;'
else
';' end
as UpdateStatement
from (
select
ss.name SchemaName,
so.name TableName,
so.id ObjectId,
st.name AS StatsName,
STATS_DATE(st.object_id, st.stats_id) AS LastStatisticsUpdateDate
, si.RowModCtr
, (select case si2.RowCnt when 0 then 1 else si2.RowCnt end from sysindexes si2 where si2.id = si.id and si2.indid in (0,1)) RowCnt
from sys.stats st
join sysindexes si on st.object_id = si.id and st.stats_id = si.indid
join sysobjects so on so.id = si.id and so.xtype = 'U' --user table
join sys.schemas ss on ss.schema_id = so.uid
) stats
where cast(stats.RowModCtr as float)/cast(stats.RowCnt as FLOAT)*100 >= 10 --more than 10% of the rows have changed
or ( --update statistics that were not updated for more than 3 months (and rows no > 0)
datediff(month, stats.LastStatisticsUpdateDate, getdate()) >= 3
and stats.RowCnt > 0
)
Qui ottengo tutti gli oggetti in cui le statistiche non sono state aggiornate per più di 3 mesi o dall'ultimo aggiornamento delle statistiche ha cambiato più del 10% delle righe.
where col=(cast @var...)) e@varpotrebbero esserlo'%'. L'ho ereditato solo una settimana o due fa e devo mantenerlo sostanzialmente funzionante fino a quando non viene sostituito. Grazie per il link, ci proverò.