On utilise les jointures lorsque l'on veut sélectionner des champs sur plusieurs tables qui sont mises en relation.
Soit les tables client, categorie et commune que nous avons utilisées pour la requête d'insertion (1-1)(1-n):
Le MCD:
Le MLD:
client: id_cli, nom_cli, preno_cli, adres_cli, id_cat, id_com
categorie: id_cat, nom_cat, pourc_cat
commune: id_com, nom_com, codep_com
Si nous voulons afficher le nom du client, sa catégorie et sa commune de résidence nous devons:
- sélectionner le nom dans la table client
- récupérer l'id de la catégorie du client dans la table client
- sélectionner la catégorie du client dans la table catégorie
- récupérer l'id de la commune du client dans la table client
- sélectionner la commune du client dans la table commune
- C'est un peu long isn't it?
On va tout faire en une seule commande, beter nee?
Principe des jointures
Imaginons les occurences suivantes au sein de nos trois tables:
id_cli |
nom_cli |
preno_cli |
adres_cli |
id_cat |
id_com |
1 |
Vandeput |
Mohamed |
rue Zbé 69 |
3 |
2 |
2 |
El Ajoui |
Stéphanie |
rue d'Aerschot 96 |
2 |
5 |
3 |
Martel |
Charles |
rue de la Liberté 1 |
1 |
4 |
4 |
Marie-Martine |
Simple |
rue Doof 17 |
2 |
4 |
---------------------------------------------------------
id_cat |
nom_cat |
pourc_cat |
1 |
Parastatal |
20 |
2 |
Particulier |
0 |
3 |
Société |
15 |
4 |
ASBL |
15 |
--------------------------------------------
id_com |
nom_com |
codep_com |
1 |
Bruxelles |
1000 |
2 |
Schaerbeeck |
1030 |
3 |
Auderghem |
1160 |
4 |
Ixelles |
1140 |
5 |
Molenbeeck |
1180 |
Quand on fait une jointure, on crée une table virtuelle et temporaire qui reprend toutes les colonnes des tables liées, donc:
id_cli |
nom_cli |
preno_cli |
adres_cli |
id_cat |
id_com |
|
id_cat |
nom_cat |
pourc_cat |
|
id_com |
nom_com |
codep_com |
1 |
Vandeput |
Mohamed |
rue Zbé 69 |
3 |
2 |
|
3 |
Société |
15 |
|
2 |
Schaerbeeck |
1030 |
2 |
El Ajoui |
Stéphanie |
rue d'Aerschot 96 |
2 |
5 |
|
2 |
Particulier |
0 |
|
5 |
Molenbeeck |
1180 |
3 |
Martel |
Charlesz |
rue de la Liberté 1 |
1 |
4 |
|
1 |
Parastatal |
20 |
|
3 |
Auderghem |
1160 |
4 |
Marie-Martine |
Simple |
rue Doof 17 |
2 |
5 |
|
2 |
Particulier |
0 |
|
2 |
Schaerbeeck |
1130 |
On constate que la table virtuelle a aligné sur une même ligne les occurences liées, dès ce moment on peut parcourir chaque ligne et tirer
les informations de notre choix.
Les jointures internes
Une jointure interne est une jointure pour laquelle il y a une donnée équivalente de part et d'autre de la jointure.
Dans notre exemple, on constate que les tables client et categorie partagent la donné id_cat, les tables client et commune partagent
la donnée id_com.
- on précise d'abord les champs que l'on veut récupérer, ils peuvent provenir des trois tables
- from: de la première table, client, celle sur laquelle on travaille
- inner join: permet de joindre la table categorie à la table client
- on: sur le critère: l'égalité entre les id_cat des tables client et categorie
- inner join: permet de joindre la table commune à la table client
- on: sur le critère: l'égalité entre les id_com des tables client et commune
- WHERE: dans la table virtuelle je sélectionne les lignes qui ont la valeur "Particulier" par exemple
$req = "
select nom_cli, nom_cat, nom_com
from client
inner join categorie
on client.id_cat= categorie.id_cat
inner join commune
on client.id_com = commune.id_com
WHERE nom.cat = "Particulier"
";
On utilise souvent une syntaxe particulière, celle du "surnommage": on surnomme client en CL, catégorie en CA et commune CO:
$req = "
select nom_cli, nom_cat, nom_com
from client CL
inner join categorie CA
on CL.id_cat= CA.id_cat
inner join commune CO
on CL.id_com = CO.id_com
WHERE nom.cat = "Particulier"
";
Les clause where, order by et limit sont bien sûr toujours valables:
Nous voulons toujours récupérer les nom, catégorie et commune des clients mais uniquement pour ceux dont le nom commence par la lettre "L", on désire un résultat par ordre alphabétique
sur le nom du client:
$req = "
select nom_cli, nom_cat, nom_com
from client CL
inner join categorie CA
on CL.id_cat= CA.id_cat
inner join commune CO
on CL.id_com = CO.id_com
where CL.nom_cli> 'L'&& CL.nom_cli < 'M'
order by CL.nom_cli asc
";
Les clauses where, order by et limit se placent après les jointures.
Les jointures externes
Les jointures externes, en plus de sélectionner l'ensemble des lignes des
tables respectant le critère de jointure comme le font les jointures internes, elles sélectionnent aussi les données d'une des tables qui ne respectent pas le critère de jointure.
Il existe des jointures par la gauche et des jointures par la droite.
Comment les distinguer?
C'est simple!
Lorsqu'on fait une jointure par la gauche, cela signifie que l'on veut toutes les lignes de la tables de gauche, celle qui suit le mot FROM,
même si celles-ci n'ont pas de correrspondance avec une ligne de la table de droite.
Lorsqu'on fait une jointure par la droite, c'est exactement l'inverse, cela signifie que l'on veut toutes les lignes de la tables de droite,
même si celles-ci n'ont pas de correrspondance avec une ligne de la table de gauche, celle qui suit le mot FROM.
LEFT JOIN
Le left join implique que l'on sélectionne toutes les lignes respectant le critère de jointure, puis on ajoute toutes les lignes
de la table "TableGauche" qui ont été rejetées car elles ne respectaient pas le critère de jointure.
Imaginons un client pour lequel la catégorie n'a pas été enregistrée, par exemple car nous n'avons pas encore cette information, et dont nous voulons
afficher quand même les informations:
$req = "
select nom_cli, nom_cat, nom_com
from client CL
left join categorie CA
on CL.id_cat= CA.id_cat
inner join commune CO
on CL.id_com = CO.id_com
";
RIGHT JOIN
Le right join implique que l'on sélectionne toutes les lignes respectant le critère de jointure,
puis on ajoute toutes les lignes de la table "TableDroite" qui ont été rejetées car elles ne respectaient pas le critère de jointure.
Imaginons un client pour lequel la catégorie n'a pas été enregistrée, par exemple car nous n'avons pas encore cette information, et dont nous voulons
afficher quand même les informations. En plus nous avons un code postal auquel nous n'avons pas de client et nous voulons l'afficher:
$req = "
select nom_cli, nom_cat, nom_com
from client CL
left join categorie CA
on CL.id_cat= CA.id_cat
right join commune CO
on CL.id_com = CO.id_com
";