Ho trovato una soluzione.
Innanzi tutto definisco la seguente vista:
codice:
CREATE VIEW ElencoPizzeIngredienti AS
SELECT P.Codice, P.Nome, P.Prezzo, P.Data, P.Preferenze, C.Ingrediente
FROM Pizza P, Composizione C
WHERE P.Codice = C.Pizza;
Se i dati fossero tali che:
codice:
mysql> SELECT * FROM ElencoPizzeIngredienti;
+--------+-------------+--------+------------+------------+------------------+
| Codice | Nome | Prezzo | Data | Preferenze | Ingrediente |
+--------+-------------+--------+------------+------------+------------------+
| 1 | Margherita | 4.50 | 2011-12-14 | 0 | Mozzarella |
| 1 | Margherita | 4.50 | 2011-12-14 | 0 | Pomodoro |
| 2 | Capricciosa | 6.50 | 2011-12-14 | 0 | Carciofi |
| 2 | Capricciosa | 6.50 | 2011-12-14 | 0 | Funghi |
| 2 | Capricciosa | 6.50 | 2011-12-14 | 0 | Mozzarella |
| 2 | Capricciosa | 6.50 | 2011-12-14 | 0 | Pomodoro |
| 2 | Capricciosa | 6.50 | 2011-12-14 | 0 | Prosciutto cotto |
| 3 | Bresaola | 7.50 | 2011-12-16 | 0 | Bresaola |
| 3 | Bresaola | 7.50 | 2011-12-16 | 0 | Grana |
| 3 | Bresaola | 7.50 | 2011-12-16 | 0 | Mozzarella |
| 3 | Bresaola | 7.50 | 2011-12-16 | 0 | Pomodoro |
| 3 | Bresaola | 7.50 | 2011-12-16 | 0 | Rucola |
| 4 | Marinara | 4.00 | 2011-12-18 | 0 | Aglio |
| 4 | Marinara | 4.00 | 2011-12-18 | 0 | Pomodoro |
+--------+-------------+--------+------------+------------+------------------+
Con la seguente interrogazione estraggo solo le pizze i quali ingredienti comprendono Pomodoro e Carciofi:
codice:
SELECT *
FROM ElencoPizzeIngredienti
WHERE Codice IN (SELECT Codice
FROM ElencoPizzeIngredienti
WHERE Ingrediente = 'Pomodoro' OR Ingrediente = 'Carciofi'
GROUP BY Codice
HAVING COUNT(DISTINCT Ingrediente) = 2);
Ovviamente la ricerca può essere estesa ad un numero di ingredienti qualsiasi, basta aggiungere (o togliere) una condizione Ingrediente = 'IngredienteDaFiltrare' nella clausola WHERE della SELECT interna e aggiornare il numero degli ingredienti (COUNT(DISTINCT Ingrediente)) su cui si effettua la selezione.
Ora ciò che voglio fare è automatizzare il tutto con una PROCEDURE. MySQL non permette il passaggio di array, perciò passerò l'elenco degli ingredienti tramite un campo TEXT correttamente formattato; ad esempio separando gli ingredienti dal carattere punto.
La procedure deve compiere due operazioni sul parametro in ingresso:
1. calcolare il numero degli ingredienti
2. costruire la clausola WHERE della SELECT interna come nell'esempio
L'operazione 1 non è un problema, supponendo (come già accennato) di formattare il parametro in ingresso separando gli ingredienti per mezzo del carattere punto, il seguente codice setta la variabile NumeroIngredienti al valore 3:
codice:
DECLARE Ingredienti TEXT;
DECLARE NumeroIngredienti SMALLINT;
SET Ingredienti = 'Pomodoro.Mozzarella.Carciofi';
SELECT 1 + CHAR_LENGTH(Ingredienti) - CHAR_LENGTH(REPLACE(Ingredienti, '.', '')) INTO NumeroIngredienti;
Il problema nasce con l'operazione 2, il parametro Ingredienti deve essere trasformato nella stringa Ingrediente = 'Ingrediente1' OR Ingrediente = 'Ingrediente2' OR ..., e fin qui nulla di difficile, il vero ostacolo è far riconoscere la stringa generata come parametro della clausola WHERE. Infatti, supponendo di avere una stringa già correttamente formattata, MySQL non interpreta come vorrei (evidentemente per ovvi motivi a me ignari) la seguente istruzione:
codice:
DECLARE Ingredienti TEXT;
SET Ingredienti = 'Ingrediente = \\'Pomodoro\\' OR Ingrediente = \\'Mozzarella\\' OR \\'Carciofi\\'';
SELECT * FROM ElencoPizzeIngredienti WHERE Ingredienti;
In particolare mi restituisce un "empty set".
Qualcuno ha qualche soluzione al problema oppure qualche altra strada per raggiungere il mio scopo?
Grazie mille!