Documenti di Didattica
Documenti di Professioni
Documenti di Cultura
eri
Sapienza Università di Roma
gn
Corso di Basi di Dati
A.A. 2014/2015
ge
In
E5 – SQL : Interrogazioni nidificate
Esercitazione
re
ive
eri
ESERCIZIO : Siano date le seguenti relazioni
gn
Fornitori(fid:integer, fnome:string, indirizzo:string)
Pezzi(pid:integer, pnome:string, colore:string)
ge
Catalogo(fid:integer, pid:integer, costo:real)
•
•
In
Per le relazioni sussistono i seguenti vincoli di integrità:
Fornitori.fid è CHIAVE PRIMARIA di Fornitori
Pezzi.pid è CHIAVE PRIMARIA di Pezzi
re
• Catalogo.fid e Catalogo.pid sono CHIAVE PRIMARIA di Catalogo
• Catalogo.fid è CHIAVE ESTERNA verso Fornitori.fid
ive
eri
ESERCIZIO : Siano date le seguenti relazioni
gn
Fornitori(fid:string, fnome:string, indirizzo:string)
Pezzi(pid:string, pnome:string, colore:string)
ge
Catalogo(fid:string, pid:string, costo:real)
eri
gn
7. Trovare i fid dei fornitori che forniscono solo pezzi rossi
8. Trovare i fid dei fornitori che forniscono un pezzo rosso e un pezzo verde
9. Trovare i fid dei fornitori che forniscono un pezzo rosso o uno verde
ge
10. Trovare i pid dei pezzi forniti da almeno due fornitori
In
re
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
1) Trovare i pnome dei pezzi per cui esiste un qualche fornitore
ge
SELECT DISTINCT P.pnome
FROM Pezzi P, Catalogo C
WHERE P.pid = C.pid
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
2) Trovare gli fnome dei fornitori che forniscono ogni pezzo
L’interrogazione interna va valutata e
ge
SELECT DISTINCT F.fnome
ri-calcolata per ogni tupla di Fornitori
FROM Fornitori F definita nell’interrogazione esterna.
WHERE NOT EXISTS (
A EXCEPT B
- Viene restituita una relazioneIn
che contiene tutti i pid dei pezzi
non forniti dal fornitore i-
(SELECT P.pid FROM Pezzi P)
EXCEPT
(SELECT C.Pid
FROM Catalogo C
WHERE C.fid = F.fid)
A. (SELECT P.Pid FROM Pezzi P)
- Calcola i pid di tutti i pezzi.
re
esimo. Se tale relazione è vuota, B. (SELECT C.Pid FROM Catalogo C
significa che il fornitore i-esimo
)
WHERE C.fid=F.fid)
fornisce tutti i pezzi. -Calcola i pid dei pezzi venduti dal
In quest’ultimo caso, NOT
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
2) Trovare gli fnome dei fornitori che forniscono ogni pezzo (sol. alternativa)
ge
SELECT DISTINCT F.fnome
FROM Fornitori F
WHERE NOT EXISTS (
Sostituzione di EXCEPT con
In
SELECT P.pid
FROM Pezzi P
WHERE P.pid NOT IN
(SELECT C.Pid
FROM Catalogo C
NOT IN, in modo da rendere la
query leggibile anche da MySQL.
re
WHERE C.fid = F.fid)
)
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
3) Trovare gli fnome dei fornitori che forniscono tutti i pezzi rossi
L’interrogazione interna va valutata e ri-
ge
SELECT DISTINCT F.fnome calcolata per ogni tupla di Fornitori
FROM Fornitori F definita nell’interrogazione esterna.
WHERE NOT EXISTS (
A EXCEPT B
In
- Viene restituita una relazione che
contiene tutti quei pezzi di colore rosso
non forniti dal fornitore i-esimo. Se
tale relazione è vuota, significa che il
(SELECT * FROM Pezzi P
WHERE P.colore = ‘Rosso’)
EXCEPT
(SELECT P1.Pid, P1.colore, A. (SELECT * FROM Pezzi P)
P1.pnome - Calcola tutti i pezzi di colore rosso
re
fornitore i-esimo fornisce tutti i pezzi
esistenti di colore rosso (ciò non vuol FROM Catalogo C, Pezzi P1
dire che il fornitore i-esimo non possa WHERE C.fid = F.fid AND B. (SELECT P1.Pid, P1.colore,
P1.pnome FROM Catalogo C, Pezzi
fornire pezzi anche di altro
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
3) Trovare gli fnome dei fornitori che forniscono tutti i pezzi rossi (sol.alternativa)
Sostituzione di EXCEPT con
ge
SELECT DISTINCT F.fnome
NOT IN, in modo da rendere la
FROM Fornitori F query leggibile anche da MySQL.
WHERE NOT EXISTS (
In
(SELECT * FROM Pezzi P
WHERE P.colore = ‘Rosso’)
NOT IN
(SELECT P1.Pid, P1.colore, P1.pnome
FROM Catalogo C, Pezzi P1
re
WHERE C.fid = F.fid AND C.pid = P1.pid)
)
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
4) Trovare i pezzi forniti dalla ACME e da nessun altra
ge
SELECT P.pid, P.pnome, P.colore
FROM Pezzi P, Catalogo C, Fornitori F
WHERE P.pid=C.pid AND C.fid=F.fid AND F.fnome = ‘ACME’ AND
)
In
NOT EXISTS (SELECT * FROM Catalogo C1, Fornitori F1
WHERE P.pid = C1.pid AND C1.fid=F1.fid AND
F1.fnome <> ‘ACME’
L’interrogazione interna calcola tutti
re
Se la relazione restituita dall’interrogazione quei fornitori (il cui nome è diverso
interna è vuota, NOT EXISTS restituisce da ‘Acme’) che forniscono il pezzo
TRUE. i-esimo (che stiamo considerando
attraverso la variabile di range P
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
5) Trovare i fid dei fornitori che ricaricano su alcuni pezzi più del costo
medio di quel pezzo
ge
L’interrogazione interna calcola la
media del prezzo di vendita del pezzo
SELECT DISTINCT C.fid i-esimo considerato (C.pid).
FROM Catalogo C
In
WHERE C.costo > (SELECT AVG(C1.costo)
FROM Catalogo C1
WHERE C1.pid = C.pid
)
L’interrogazione esterna, per ciascun
pezzo fornito in catalogo, verifica che
il prezzo del pezzo considerato sia
superiore rispetto al prezzo medio di
vendita di quel pezzo (calcolato con
l’interrogazione interna).
re
In quest’ultimo caso, l’interrogazione
esterna restituisce il fid del fornitore
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
6) Per ciascun pezzo, trovare gli fnome dei fornitori che ricaricano di più su
quel pezzo
ge
L’interrogazione interna calcola il
SELECT C.pid, F.fnome massimo prezzo di vendita del pezzo i-
FROM Fornitori F, Catalogo C esimo considerato (C.pid).
WHERE C.fid = F.fid
In
AND C.costo = (SELECT MAX(C1.costo)
FROM Catalogo C1
WHERE C1.pid = C.pid
L’interrogazione esterna, per ciascun
pezzo fornito in catalogo, verifica che
il prezzo del pezzo i-esimo
considerato sia uguale al massimo
re
prezzo di vendita di quel pezzo
) (calcolato con l’interrogazione interna).
In quest’ultimo caso, l’interrogazione
esterna restituisce il nome del fornitore
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
7) Trovare i fid dei fornitori che forniscono solo pezzi rossi
ge
La prima interrogazione interna
SELECT F.fid verifica che l’i-esimo fornitore venda
FROM Fornitori F pezzi non rossi.
WHERE NOT EXISTS (SELECT *
In
FROM Pezzi P, Catalogo C1
WHERE C1.fid = F.fid AND
C1.pid = P.pid AND
P.colore <> ‘Rosso’
La seconda interrogazione esterna
verifica che l’i-esimo fornitore venda
qualcosa (per evitare che eventuali
fornitori che non vendono niente siano
inclusi nel risultato).
re
) L’interrogazione esterna inserisce il
AND EXISTS (SELECT * nome dell’i-esimo fornitore nella
relazione risultato se la prima
FROM Catalogo C1
ive
interrogazione interna restituisce una
WHERE C1.fid = F.fid) relazione vuota e la seconda
interrogazione esterna restituisce una
relazione non vuota.
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
8) Trovare i fid dei fornitori che forniscono un pezzo rosso e un pezzo verde
ge
SELECT DISTINCT C.fid La prima interrogazione calcola i fid dei
FROM Catalogo C, Pezzi P fornitori (senza duplicati) che
INTERSECT
In
WHERE C.pid = P.pid AND P.colore = ‘rosso’
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
8) Trovare i fid dei fornitori che forniscono un pezzo rosso e un pezzo verde
(soluzione alternativa)
ge
SELECT DISTINCT C.fid
FROM Catalogo C, Pezzi P
In
WHERE C.pid = P.pid AND P.colore = ‘rosso’
AND C.fid IN
(SELECT DISTINCT C1.fid
FROM Catalogo C1, Pezzi P1
re
WHERE C1.pid = P1.pid AND P1.colore = ‘verde’)
ive
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
9) Trovare i fid dei fornitori che forniscono un pezzo rosso, oppure uno
verde, oppure entrambi
ge
SELECT DISTINCT C.fid La prima interrogazione calcola i fid dei
fornitori (senza duplicati) che
FROM Catalogo C, Pezzi P
In
WHERE C.pid = P.pid AND P.colore = ‘rosso’
UNION
SELECT DISTINCT C1.fid
FROM Catalogo C1, Pezzi P1
forniscono almeno un pezzo rosso.
verde.
eri
Fornitori Pezzi Catalogo
fid fnome indirizzo pid pnome colore fid pid costo
gn
10) Trovare i pid dei pezzi forniti da almeno due fornitori
ge
SELECT DISTINCT C.pid
FROM Catalogo C
In
WHERE EXISTS (SELECT DISTINCT C1.pid
FROM Catalogo C1
WHERE C1.pid = C.pid AND
C1.fid <> C.fid) L’ i-esimo pezzo compare nel risultato
re
dell’interrogazione interna se esiste un
altro fornitore che vende quel pezzo.
ive