Vista indicizzata
Una soluzione completamente nuova basata su Viste indicizzate è possibile.
Una vista indicizzata è una vista che contiene un indice cluster e i dati sono effettivamente archiviati su disco.
A quanto ho capito, stai cercando di mantenere una somma di acquisti per articolo di prodotto archiviato in tblProduct
. Ho presupposto che ItemCode
è il PK di tblProduct e quel ItemName
è anche definito lì (non possiamo usare MAX
in una vista indicizzata). Quindi possiamo definire una vista come questa:
CREATE VIEW dbo.vwTotalPurchases
WITH SCHEMABINDING -- must be schema bound, we cannot change underlying columns after creation
AS
SELECT
ItemCode,
SUM(Quantity) QuantityPurchased,
COUNT_BIG(*) CountPurchases -- if we group, must have count also, so that rows can be maintained
FROM dbo.tblPurchase -- must use two-part names
GROUP BY itemCode;
GO
Possiamo quindi creare un indice cluster su di esso per mantenerlo su disco. SQL Server manterrà l'indice ogni volta che si verifica un aggiornamento della tabella di base. Se non ci sono più righe nel raggruppamento (identificato dal conteggio pari a 0), la riga viene eliminata:
CREATE UNIQUE CLUSTERED INDEX PK_vwTotalPurchases ON dbo.vwTotalPurchases (ItemCode);
GO
Ora, se vogliamo interrogarlo, possiamo unirci a questa vista su tblProducts
(a sinistra unisciti perché potrebbero non esserci acquisti):
SELECT
p.ItemCode,
p.ItemName,
ISNULL(tp.QuantityPurchased, 0) QuantityPurchased,
ISNULL(tp.CountPurchases, 0) CountPurchases
FROM tblProducts p
LEFT JOIN vwTotalPurchases tp WITH (NOEXPAND) ON tp.ItemCode = p.ItemCode;
Possiamo definire anche questa come una vista (non una vista indicizzata, ma una vista standard) in modo che la definizione sia utilizzabile ovunque.
Nota su NOEXPAND
:
Se non utilizzi SQL Server Enterprise o Developer Edition, devi utilizzare il suggerimento WITH (NOEXPAND)
per forzarlo a usare l'indice, altrimenti interrogherà il tblPurchase
di base invece. E anche in quelle edizioni, è meglio usare NOEXPAND
.
Vedi questo articolo di Paul White su questo.