DBCC freeproccache?

Le tue domande sono dappertutto, quindi cercherò di affrontarle tutte. La cache della procedura è solo così grande. La cache delle procedure potrebbe essere stata riempita con piani monouso (ciò non ha alcun impatto sulle statistiche, sebbene le statistiche possano influire sulla cache del piano). Puoi leggere molti dettagli sui piani monouso nel post sul blog di Kimberly Tripp, “Pianifica cache e ottimizzazione per carichi di lavoro ad hoc”, inclusa una query su sys.dm_exec_cached_plans che ti aiuterà a identificare quando la cache viene popolata con molti piani monouso. Come suggerisce lei, puoi prevenire questo gonfiore usando optimize per carichi di lavoro ad hoc. Se stai trovando la necessità di farlo spesso, direi che programmare freeproccache come lavoro è un cerotto, non una soluzione.

Per eliminare un piano “cattivo”, è necessario prima identificare il piano “cattivo”. Questo potrebbe essere un piano che supera una certa dimensione e / o non è stato eseguito da un po ‘ di tempo, o che è stato identificato da una query di lunga durata, ecc. Sfortunatamente non è semplice identificare un piano vittima dello sniffing dei parametri a meno che non si conosca già la query o le query interessate. Supponiamo che tu voglia trovare i piani più vecchi nella cache che non sono stati eseguiti da più di una settimana:

;WITH x AS ( SELECT TOP 10 qs., qs.plan_handle, txs = qs.statement_start_offset, txe = qs.statement_end_offset, = cp.size_in_bytes, = SUM(cp.usecounts), = MAX(qs.last_execution_time) FROM sys.dm_exec_query_stats AS qs INNER JOIN sys.dm_exec_cached_plans AS cp ON qs.plan_handle = cp.plan_handle WHERE qs.last_execution_time < DATEADD(DAY, -7, CURRENT_TIMESTAMP) GROUP BY qs., qs.plan_handle, cp.size_in_bytes, qs.statement_start_offset, qs.statement_end_offset ORDER BY DESC) SELECT x.plan_handle, size, uses, , = COALESCE(NULLIF( SUBSTRING(t., x.txs/2, CASE WHEN x.txe = -1 THEN 0 ELSE (x.txe - x.txs)/2 END ), ''), t.) FROM x CROSS APPLY sys.dm_exec_sql_text(x.) AS t;

Ora è necessario verificare che si vuole veramente cancellare questo piano. Ad esempio, se riconosci quella query come qualcosa che il CEO potrebbe eseguire domani, forse è meglio lasciarlo lì. Se vuoi cancellare il piano, puoi cancellarlo direttamente dicendo:

DBCC FREEPROCCACHE();

Sembra molto più lavoro che eseguire DBCC FREEPROCCACHE a livello globale, ma se hai molti buoni piani nella cache, sarà sicuramente migliore per i tuoi utenti in generale.

Ancora, questo suona davvero come un cerotto. Se la cache si sta riempiendo di spazzatura e le prestazioni vanno in bagno fino a liberare la cache, è necessario esaminare un livello superiore all’architettura, come vengono inviate le query, ecc. Questo è il comportamento che mi aspetterei dalla prima iterazione di LINQ2SQL, dove memorizzerebbe nella cache una versione di un piano per una query per ogni argomento stringa di lunghezza diversa. Quindi, se avessi un parametro di “gennaio”, avresti un piano diverso rispetto a un parametro di “febbraio” perché definirebbe il tipo di dati come VARCHAR(7) rispetto a VARCHAR(8). Abbastanza sicuro che il comportamento sia corretto, ma non ne so abbastanza del tuo ambiente / applicazione per suggerire dove esattamente cercare “cattive idee.”