Gli algoritmi delle Viste
Spiegazione
L'istruzione CREATE VIEW accetta una clausola opzionale ALGORITHM, un'estensione SQL per le Views.
Questa può assumere tre valori: MERGE, TEMPTABLE o UNDEFINED, e influenza il modo in cui MariaDB elabora le viste.
Con MERGE, la definizione della vista e la porzione delle istruzioni che si riferiscono alla vista vengono unite. Se si usa TEMPTABLE, i risultati della vista vengono inseriti in una tabella temporanea.
MERGE di solito è più efficiente, ed è possibile aggiornare le viste solo se usano questo algoritmo. TEMPTABLE può essere utile in certe situazioni, perché i lock sulle tabelle sottostanti possono essere rilasciati prima che l'esecuzione dell'istruzione sia terminata.
Se è UNDEFINED (o la clausola ALGORITHM non è specificata), MariaDB sceglie l'algoritmo migliore. L'algoritmo può essere UNDEFINED anche se è stato specificato MERGE ma questo non può essere utilizzato.
MERGE limiti
Le viste che usano le seguenti funzionalità non possono essere di tipo ALGORITHM=MERGE:
- HAVING
- LIMIT
- GROUP BY
- DISTINCT
- UNION
- UNION ALL
- Una funzione aggregante, come MAX(), MIN(), SUM() o COUNT()
- Una subquery nella lista SELECT
- Se non si basa su una tabella, e quindi estrae solo valori letterali
Esempi di MERGE
Esempio 1
Ecco un esempio di come MariaDB gestisce l'algoritmo MERGE. Prendiamo una vista definita in questo modo:
CREATE ALGORITHM = MERGE VIEW nome_vista (campo_vista1, campo_vista2) AS SELECT campo1, campo2 FROM nome_tabella WHERE campo3 > '2013-06-01';
Ora, se eseguiamo la seguente query sulla vista:
SELECT * FROM nome_vista;
per eseguire la vista, nome_vista
diventa la tabella sottostante, nome_tabella
, il *
diventa i campi campo_vista1
e campo_vista2
, che corrispondono a campo1
e campo2
e viene aggiunta la clausola WHERE, WHERE campo3 > 100
, quindi la query effettiva diventa:
SELECT campo1, campo2 FROM nome_tabella WHERE campo3 > '2013-06-01'
Esempio 2
Data la stessa vista usata sopra, eseguiamo la seguente query:
SELECT * FROM nome_vista WHERE campo_vista < 8000;
Tutto avviene come nell'esempio precedente, ma campo_vista < 8000
prende il nome del campo corrispondente e diventa campo1 < 8000
, collegato con AND
alla condizione campo3 > '2013-06-01'
.
Perciò la query risultante sarà:
SELECT campo1, campo2 FROM table_name WHERE (campo3 > '2013-06-01') AND (campo1 < 8000);
Nel collegamento tramite AND
, vengono aggiunte le parentesi in modo che le precedenze siano sempre corrette.