La structure interne ainsi que le design d'AreaProg ont récemment été modifiés.
Suite à cela, le format de certains articles a été perturbé. Le problème est connu et en cours de résolution. Merci de votre compréhension.
INNER JOIN table
[ON champ1=champ2 [{AND | OR} champ3=champ4,... ]]
Voyons comment se servir de cela grâce à un exemple. Imaginez donc tout d'abord une simple requête permettant de retrouver une personne sur base de son identifiant. La requête serait donc la suivante :
SELECT ID_PERSONNE, NOM, PRENOM, AGE FROM PERSONNES WHERE ID_PERSONNE = 3Nous allons imaginer pour l'instant que la personne recherchée sera celle dont l'identifiant correspond à 3. Voici donc le résultat renvoyé par cette requête : Jusque là, tout est normal. Nous allons maintenant joindre la table PERSONNE_VOITURE sans condition pour voir un petit peu ce que cela fait. Tapez donc :
SELECT ID_PERSONNE, NOM, PRENOM, AGE, PERSONNE_ID, VOITURE_ID, COULEUR_ID FROM PERSONNES INNER JOIN PERSONNE_VOITURE WHERE ID_PERSONNE = 3Le résultat renvoyé par cette requête est le suivant : Ce résultat est logique. Comme vous le voyez, nous commençons par sélectionner plus de champs. En effet, étant donné que nous joignons la table PERSONNE_VOITURE à la requête, les champs de cette table pourront être indiqués dans la liste des champs à sélectionner par le SELECT. Comme vous le voyez, la requête reste la même à l'exception de l'INNER JOIN. Mais si la requête reste la même, pourquoi y a-t-il 4 résultats au lieu de 1 ? La réponse est simple. La table PERSONNE_VOITURE contient 4 enregistrements et la requête sans le INNER JOIN renvoie 1 seul résultat. Pour afficher le résultat de ces deux requêtes ensemble, il y aura 4 résultats. Si nous disons que le SELECT sans l'INNER JOIN est la requête S et que l'INNER JOIN est la requête I, le résultat renvoyé est le suivant : Enregistrement de S suivi du premier enregistrement de I Enregistrement de S suivi du deuxième enregistrement de I Enregistrement de S suivi du troisième enregistrement de I Enregistrement de S suivi du quatrième enregistrement de I Les résultats sont donc combinés entre eux pour qu'ils apparaissent tous. Bien évidemment ici, tout ne nous intèresse pas. Regardez par exemple la première ligne. le champ PERSONNE_ID vaut 2 et non 3, c'est donc un enregistrement qui concerne la personne 2, cet enregistrement n'a donc rien à faire dans le résultat. Il est néanmoins présent car nous n'avons pas stipulé de condition à la jointure. Ce type de condition s'indique grâce au mot clé ON juste après la jointure. Tapez par exemple cette requête :
SELECT ID_PERSONNE, NOM, PRENOM, AGE, PERSONNE_ID, VOITURE_ID, COULEUR_ID FROM PERSONNES INNER JOIN PERSONNE_VOITURE ON ID_PERSONNE = PERSONNE_ID WHERE ID_PERSONNE = 3Le ON fonctionne comme le WHERE, il est donc possible de préciser plusieurs conditions séparées par des AND ou OR. Ici, nous joignons encore une fois la table PERSONNE_VOITURE à la sélection, mais nous ne joignons que les enregistrements où le champ ID_PERSONNE de la table PERSONNES est le même que le champ PERSONNE_ID de la table PERSONNE_VOITURE. Ainsi, tous les enregistrements joints concernent la personne ayant l'identifiant 3. La preuve : Nous avançons bien, mais ce n'est pas fini. Effectivement, maintenant que nous avons l'identifiant des voitures que la personne possède ainsi que l'identifiant de leur couleur, il serait plus agréable de récupérer leur intitulé. Il suffit simplement de faire deux autres INNER JOIN. Voyons d'abord celui pour la voiture :
SELECT ID_PERSONNE, NOM, PRENOM, AGE, PERSONNE_ID, MARQUE, COULEUR_ID FROM PERSONNES INNER JOIN PERSONNE_VOITURE ON ID_PERSONNE = PERSONNE_ID INNER JOIN VOITURES ON ID_VOITURE = VOITURE_ID WHERE ID_PERSONNE = 3Le résultat renvoyé par cette requête est le suivant : Comme vous le voyez, cette fois, c'est la marque de la voiture et non plus l'identifiant qui apparaît. C'est réalisé très simplement. On commence par joindre la table VOITURES au résultat obtenu précédemment mais comme nous ne voulons que les voitures appartenant à la personne en question, on pose une condition grâce au ON qui ne joindra aux lignes du résultats QUE les liens dont l'identifiant récupéré dans la table PERSONNE_VOITURE sera le même que dans le champ ID_VOITURE de la table VOITURES. Modifions maintenant une dernière fois la requête pour récupérer uniquement les champs qui nous interesse mais également pour récupérer l'intitulé de la couleur de la voiture :
SELECT NOM, PRENOM, AGE, MARQUE, COULEUR FROM PERSONNES INNER JOIN PERSONNE_VOITURE ON ID_PERSONNE = PERSONNE_ID INNER JOIN VOITURES ON ID_VOITURE = VOITURE_ID INNER JOIN COULEURS ON ID_COULEUR = COULEUR_ID WHERE ID_PERSONNE = 3L'exécution de cette requête produirait le résultat suivant : Youhou o/ C'est ce qu'on voulait. La première différence avec cette requête et les précédentes est le fait que nous ne sélectionnons plus que les champs qui nous interessent. Inutile de sélectionner le champ PERSONNE_ID vu qu'on le connait car c'est sur cela que porte la condition après le WHERE. Ensuite, nous avons à nouveau joint une nouvelle table. Cette fois, c'est COULEURS que nous joignons et encore une fois nous joignons cette table selon une condition comme quoi le champ ID_COULEUR de cette table doit être égal au champ COULEUR_ID récupéré de la table PERSONNE_VOITURE. Vous allez voir que les jointures internes sont bien mais souffrent d'un problème que les jointures externes peuvent facilement régler. Vous allez voir cela tout de suite.
SELECT NOM, PRENOM, AGE, MARQUE, COULEUR FROM PERSONNES INNER JOIN PERSONNE_VOITURE ON ID_PERSONNE = PERSONNE_ID INNER JOIN VOITURES ON ID_VOITURE = VOITURE_ID INNER JOIN COULEURS ON ID_COULEUR = COULEUR_ID WHERE ID_PERSONNE = 3Nous avons vu qu'elle fonctionnait très bien avec la personne dont l'identifiant valait 3. Essayez maintenant d'exécuter cette requête avec l'identifiant 1. Si vous le faites, vous verrez qu'aucun résultat n'est renvoyé. C'est étrange car même si la personne 1 ne possède pas de voiture, cette personne existe. C'est en fait une réaction normale. Effectivement, lorsque les INNER JOIN sont évalués, les tables sont jointes et ce, généralement sous condition. Si une condition n'est pas respectée, donc qu'aucun ligne de la table distante ne peut être jointe, aucun résultat ne sera renvoyé. Ici, quand la première jointure va être exécutée, donc celle qui joint PERSONNES à PERSONNE_VOITURE, aucune ligne ne pourra être jointe. Effectivement, aucune ligne de la table PERSONNE_VOITURE ne contient d'enregistrement avec le champ PERSONNE_ID valant 1. Aucune ligne ne sera donc jointe et aucune ligne ne sera renvoyée en résultat. Sachez qu'il existe trois types de jointures externes. Les gauches, les complètes et les droites. La différence n'est pas énorme. Dans le cas des jointures externe gauche, on rajoute les lignes de la table de gauche qui n'ont pas été prises en compte. Dans le cas d'une jointure droite, ce sont les lignes de la table de droite qui n'ont pas été prises en compte qui sont rajoutées. Enfin, les jointures externes complètes ajoutent les lignes de la table qui n'ont pas été prises en compte de gauche et de celle de droite. La table de gauche est celle qui apparaît dans la requête SQL AVANT le mot clé de jointure, tandis que celle de droite est celle qui apparaît APRES le mot clé de jointure. La syntaxe d'une jointure externe est la suivante :<br /><br />
LEFT | RIGHT | FULL OUTER JOIN table_droite ON conditionVous devez choisir entre LEFT (gauche), FULL (complète) ou RIGHT (droite). Le mot clé OUTER n'est pas obligatoire mais bon, nous vous conseillons de le mettre pour la clarté de votre requête. Nous allons maintenant modifier la requête précédente pour voir un petit peu le fonctionnement des jointures externes. Remplacez donc tout les INNER par des LEFT OUTER pour donner ceci :
SELECT NOM, PRENOM, AGE, MARQUE, COULEUR FROM PERSONNES LEFT OUTER JOIN PERSONNE_VOITURE ON ID_PERSONNE = PERSONNE_ID LEFT OUTER JOIN VOITURES ON ID_VOITURE = VOITURE_ID LEFT OUTER JOIN COULEURS ON ID_COULEUR = COULEUR_ID WHERE ID_PERSONNE = 1L'exécution de cette requête donnera : Comme vous le voyez, il y a du mieux. Nous avons maintenant récupérer une ligne avec des valeurs nulles. Ce résultat est logique. En effet, la première jointure joint la table PERSONNES et PERSONNE_VOITURE, mais la table PERSONNE_VOITURE ne contient aucun enregistrement avec le champ PERSONNE_ID contenant 1, une jointure interne échouerait donc. La jointure externe, elle, va joindre une ligne de résultat contenant NULL comme valeur pour PERSONNE_ID et VOITURE_ID. Les deux jointures externes suivantes vont procéder de la même façon car elles vont essayer de joindre des tables dans leqsuelles des champs vaudront NULL. En effet, VOITURE_ID valant NULL après la première jointure, la requête va essayer de joindre la table VOITURES avec la ligne qui contient NULL dans le champ ID_VOITURE. Il n'existe pas d'enregistrement de ce type. C'est donc la valeur NULL qui sera jointe. Il en ira de même avec la table COULEURS. Nous pourrions voir dans ce cours un tas d'autres exemples, mais une bonne compréhension du SQL passe par la répetition. En effet, vous devez faire et refaire plein de commandes différentes et analyser les résultats pour bien comprendre les comportement des mots clé que vous utilisez. Je vous conseille donc de faire le plus de jointures possibles pour bien comprendre leur fonctionnement car c'est vraiment très importante et utile. Il reste d'autres types de jointure, mais je ne les connais pas. Le cours sera donc mis à jour une fois que j'aurais appris leur fonctionnement.
Veuillez vous identifier ou vous inscrire pour donner une note à cet article.
Veuillez vous identifier ou vous inscrire pour réagir à cet article.
Nico (04/01/2010 - 18:44)
Loulou (09/01/2010 - 11:58)
Mystère (25/02/2010 - 14:00)
KyleKatarn (27/02/2010 - 12:08)
Cet article vient vraiment de m'ouvrir de belles possibilités.
Anouar (15/05/2010 - 23:51)
ice (18/06/2010 - 21:09)
Sherlock (24/08/2010 - 10:55)
Juste une petite remarque, dans la dernière requête ID_Personne = 1
Lois (23/10/2010 - 09:23)
Selon ce schéma, quelle requête pour sélectionner les personnes qui ont à la fois une BMW et une mercedes ?
Peter (15/12/2010 - 11:03)
c ca (05/01/2011 - 10:47)
Sébastien Sougnez (05/01/2011 - 10:52)
Pas envie d'être plus clair ?
c ca (05/01/2011 - 11:43)
FROM PERSONNES
INNER JOIN PERSONNE_VOITURE
WHERE ID_PERSONNE = 3
ca marche pas
impossible de mettre 'inner' sans 'on'
espece de banane
Sébastien Sougnez (05/01/2011 - 12:09)
je te trouve un peu généraliste. As-tu remarqué que les cours étaient axés sur une base de données MySQL ? Selon les captures d'écran, il est évident que nous sommes sous phpMyAdmin.
Je viens de tester sur mon environnement MySQL et un INNER JOIN sans "ON" fonctionne...
Sans compter que la commande montrée était juste un exemple permettant d'introduire la syntaxe correcte d'INNER JOIN...
Alors avant de monter sur tes grand chevaux et de te ridiculiser sur un site, renseigne toi ;-)
Las (07/01/2011 - 11:11)
@all. Arrêter de vs en prendre à seb. Vs ne pouvez pas imaginez ce que cela peut representer en terme d'effort et de tps pr mettre en place un tuto aussi simple qu'il soit.
@Lois : pour sélectionner les personnes qui ont à la fois une BMW et une mercedes, je ferais, en +sieurs sous requetes pr etre claire pour le novice en sql que je suis :
Tab1 = les personnes qui ont une BMW
Tab2 = les personnes qui ont une mercedes
et apres le fais T1 INTER T2 (select * from Tab1 where personne_id in (select personne_id from Tab2)).
Brice (28/01/2011 - 14:21)
Reda (23/02/2011 - 11:54)
ZEMZEMI Amine (10/03/2011 - 11:07)
Je vous félicite pour la qualité du tuto.
Une petite remarque concernant la dernière requête (Jointure Externe), je pense qu'il faut mettre 1 à la place de 3.
WHERE ID_PERSONNE = 1
En effet, on souhaite tester sur la personne dont son ID=1 et qui n'a pas de voiture.
Cordialement
cmini (09/06/2011 - 17:08)
MOH (28/06/2011 - 14:24)
Stef (06/07/2011 - 10:49)
PrineJ (11/07/2011 - 09:16)
BIHI (13/07/2011 - 16:58)
Mohamed (17/07/2011 - 21:59)
Michèle (21/07/2011 - 14:41)
Gaspard (29/07/2011 - 02:28)
cdlt
Cheikh (10/08/2011 - 17:21)
Internaute (12/08/2011 - 16:33)
Jean-Marc (23/11/2011 - 18:46)
didi (24/11/2011 - 17:54)
Djebbi (29/12/2011 - 11:52)
Othmane (30/12/2011 - 00:00)
Kaia (04/01/2012 - 10:20)
Batiatus (08/01/2012 - 18:13)
b-karoten (13/01/2012 - 20:47)
Comment faire si l'on désire récupérer toute une table SAUF les entrées ayant un id présent en tant que FK dans une seconde table ?
tkf (15/02/2012 - 23:12)
Empty (21/02/2012 - 12:33)
cedric (21/02/2012 - 16:05)
Hassan (21/02/2012 - 17:37)
khaled (05/03/2012 - 22:34)
BD56 (06/03/2012 - 22:05)
Ton exemple pour la jointure interne n'est pas significatif car on peut faire la même chose sans le mot clé INNER JOIN :
SELECT NOM, PRENOM, AGE, MARQUE, COULEUR
FROM PERSONNES, VOITURES, COULEURS, PERSONNE_VOITURE
WHERE ID_PERSONNE = 3 AND ID_COULEUR = COULEUR_ID AND ID_VOITURE = VOITURE_ID
AND ID_PERSONNE = PERSONNE_ID
Aymen (10/04/2012 - 01:31)
Azzedidne (12/04/2012 - 20:39)
farid (23/04/2012 - 15:49)
Kicoe (03/05/2012 - 09:35)
Yassine (16/05/2012 - 14:35)
ta mère (31/05/2012 - 11:14)
Jeff (06/06/2012 - 12:13)
Bonne continuation !
Jamic (13/06/2012 - 17:18)
Je pense qu'il aurait fallu systématiquement mentionner les clauses ON.
Elles ne sont peut-être pas indispensables sous MySQL mais elles font partie intégrante de la syntaxe et elles sont indispensables dans d'autres SGBD.
De la même manière (mais à linverse), le terme INNER n'est pas toujours obligatoire.
hello (09/07/2012 - 14:15)
tu devrais un peu mieux lire; comme l'explique le monsieur l'inner join va rassembler le resultat au fur et à mesure. tandis que ta requete va rassembler l'integralité des tables ensemble et ne chercher les paramètres qu'ensuite. bref tu va faire exploser ta base de donnée et te faire passer pour un débutant.
Alexandra (06/11/2012 - 11:50)
Merci d'avoir pris le temps de tout décrire.
Je ne suis pas spécialement novice mais j'aime beaucoup reprendre les bases quand une problématique se pose à moi!
Axel (10/11/2012 - 21:01)
Très clair et bien expliqué
Eroca (15/11/2012 - 12:11)
Thierry (19/11/2012 - 15:10)
abou (23/11/2012 - 09:43)
cette explication est très claire. Elle m'a permis d'améliorer considérablement mes constructions de requêtes.
Maître Capello (03/12/2012 - 13:59)
Nous avons maintenant récupérer -> Nous avons maintenant récupéré
leqsuelles -> lesquelles
B&Y (03/12/2012 - 15:18)
yvesnomade83 (05/12/2012 - 16:40)
ps: je suis sous access et INNER JOIN n'a pas fonctionné à partir de 2 de suite... impossible de mettre avec and ... j'ai réussi en changeant tout et en mettant à la place le paragraphe d'un autre commentaire
mais merci pour l'explication qui m'aide beaucoup pour la création de mon petit programme de vente, stock
Anonyme (13/12/2012 - 11:33)
Moux (25/12/2012 - 02:03)
Lucie (14/01/2013 - 17:07)
Malek (17/01/2013 - 16:40)
Simple claire et surtout efficace !
Je n'avais jamais compris la différence et l'idée d'aller chercher dans des docs interminables me faisait faire demi-tour ... pour ma part la phrase qui ma le plus fait ouvrir le cerveau c'est "... La table de gauche est celle qui apparaît dans la requête SQL AVANT le mot clé de jointure, tandis que celle de droite est celle qui apparaît APRES le mot clé de jointure ... " c'est de CA dont j'avais besoin ...Merciiiiiii
Mohamed (22/01/2013 - 23:11)
pihug12 (24/01/2013 - 10:54)
Pourrais-je savoir avec quel logiciel a été fait le 1er schéma ?
Merci d'avance.
Michoco (03/02/2013 - 18:57)
Très bon tutoriel.
Sinon si j'ai bien compris le outer join c'est comme le inner join mais en "mieux" si je puis dire ?
Mamad (05/02/2013 - 09:06)
Monssif Chrit (07/02/2013 - 20:31)
booraq (25/02/2013 - 19:00)
Aksel (18/04/2013 - 10:55)
merci pour cet article, j'ai juste une petite question, avec quel outils vous avez fait la conception de votre BDD (le premier schéma)?
Merci.
Sebastien (07/05/2013 - 15:31)
Maxoss (09/05/2013 - 20:26)