transparents

Transcription

transparents
Bases de données
cours4
www.liafa.univ-paris-diderot.fr/~zielonka
Requêtes imbriquées
Dans WHERE ou dans HAVING :
attribut = (SELECT …)
attribut <= (SELECT …)
attribut < (SELECT …) etc.
Restriction :
ce type de condition est valable uniquement si SELECT
retourne une seule valeur.
personne
nom
prenom salaire
McQuin
John
Trouver la (les) personne(s) qui
32000
gagne(nt) le plus.
Dupont
Marc
50000
Lopez
Anne
45000
Joly
Angela
10000
select max(salaire) from personne;
select nom, prénom
from personne where salaire = ? ;
Combiner les deux requêtes :
select nom, prenom
from personne
where salaire = (select max(salaire)
from personne);
Quelle différence avec la requête suivante ?
select nom, prénom
from personne
order by salaire desc nulls last
limit 1;
Et si plusieurs personnes avec le salaire max ?
Trouver toutes les personnes qui gagnent plus que la
moyenne?
select nom , prénom
from personne
where salaire > (select avg(salaire)
from personne);
Dans la BD Bibliothèque trouver le nombre d’exemplaires du
livre ‘La reine Margot’ :
select count(*)
from exemplaire
where id_livre = (select id_livre
from livre
where titre = 'La reine Margot');
On ajoute le département où travaille chaque employé :
personne(nom, prénom, salaire, département)
trouver les département dont les salaires moyens sont plus
élevés que le salaire moyen de l’entreprise :
select département
from personne
group by department
having avg(salaire) > (select avg(salaire)
from personne);
Trouver les lecteurs qui ont emprunté plus que la moyenne
en 2015 :
D’abord la moyenne d’emprunts :
(nombre d’emprunts en 2015) / (nombre de lecteurs)
(select count(*)
from emprunt
where extract (year from date_emprunt)=2015 ) /
(select count(*) from lecteur)
Pour éviter le problème d’arrondi :
cast((select count(*)
from emprunt
where extract (year from date_emprunt)=2015 ) as float)/
(select count(*) from lecteur);
select nom, prénom
from lecteur natural join emprunt
where extract(year from date_emprunt) = 2015
group by id_lecteur, nom, prénom
having count(*) >=
cast((select count(*)
from emprunt
where extract (year from date_emprunt)=2015 ) as float)/
(select count(*) from lecteur);
employe(nom,prenom,departement,salaire)
trouver les salariés qui gagnent entre 0.75 et 1.25
de salaire moyen :
select nom, prénom
from employe
where salaire between 0.75*(select avg(salaire) from employe)
and
1.25*(select avg(salaire) from employe) ;
attribut IN (select …)
attribut IN (SELECT …) est true si une de valeurs
obtenue pas SELECT est égale à la valeur de l’attribut.
La négation :
attribut NOT IN (SELECT …)
Trouver les livres qui n’ont jamais été empruntés :
select titre from livre
where id_livre NOT IN (select id_livre
from exemplaire
where id_exemplaire IN
(select id_exemplaire
from emprunt) );
ALL SOME ANY
attribut relation ANY (SELECT …)
attribut relation ALL (SELECT …)
SOME la même chose que ANY
relation
= <> <= >=
>
<
A > SOME(select …)
supposant que le résultat de select est X1,X2,…,Xn
alors la condition est équivalent à
A>X1 OR A>X2 OR … OR A>Xn
A > ALL(select …)
supposant que le résultat de select est X1,X2,…,Xn
alors la condition est équivalent à
A>X1 AND A>X2 AND … AND A>Xn
BD bibliothèque :
calculer le nombre d’exemplaires de livres
d’Alexandre Dumas
select count(id_exemplaire)
from exemplaire
where id_livre = ANY (select id_livre from
livre natural join livre_auteur
natural join auteur
where nom=‘Dumas’ and
prenom=‘Alexandre’);
employe(nom, prénom, sexe, salaire,departement)
trouver les employés qui gagnent plus que tous
les employés femmes :
select nom, prénom
from employe
where salaire > ALL (select salaire
from employe
where sexe=‘F’);
trouver les employés qui gagnent plus que les salaires
moyens dans tous les départements :
select nom, prénom
from employe
where salaire > ALL (select avg(salaire)
from employe
group by department);
trouver les départements avec le salaire moyen
le plus élevé :
select département
from employe
group by department
having avg(salaire) >= ALL(select avg(salaire)
from employe
group by department);
EXISTS
EXISTS (SELECT ….)
est vrai si SELECT retourne une table non vide.
trouver les lecteurs qui ont des emprunts non retournés :
select nom, prénom from lecteur L
where exists(select *
from emprunt E
where date_effective is null and
E.id_lecteur = L.id_lecteur);
R
D
A
B
C
X
2
1
1
X
3
8
2
X
4
2
2
Y
3
2
1
Y
4
5
2
Y
0
2
2
Z
1
3
0
Z
1
0
3
Z
0
6
7
Z
0
4
2
select D, B
from R
where A = (select max(B)
from R as S
where R.D = S.D);
R
S
a
b
c
c
d
1
8
1
2
6
3
2
3
1
13
9
1
6
2
2
11
1
2
6
-5
3
0
6
3
3
0
4
4
4
4
7
2
5
0
3
select sum(a*d) as X, C
from R natural join S
where C in (select a+1
from R)
group by C
order by x asc ;
select c, count(*) as count
from R natural left join S
where a>= 2
group by c
having count(*) > 1;