Cours SQL ORACLE – 03 : Les jointures (LEFT RIGHT FULL JOIN).

Les jointures permettent de joindre les lignes de plusieurs tables dans la même requête. Pour mieux expliquer cela, prenons comme exemple deux tables : commandes  et lignes commandes. La table des commandes comporte l’entête de chaque commande (référence de la commande, date de la commande, client etc…) alors que la table ligne commande comporte les détails de chaque ligne de commandes (article, quantité, etc…). Pour afficher une commande au complet, nous devons faire une jointure entre ces deux tables.

Il existe plusieurs types de jointure. Nous allons essayer de les voir toutes en détails :

  • Produit cartésien :

Comme en mathématique, le produit cartésien est l’ensemble de tous les couples composé par les lignes de la table 1 et la table2.

Pour réaliser, cette jointure :

SELECT * FROM table1, table2

Prenons le cas des deux tables EMP et DEPT du schéma SCOTT. Le contenu de ces deux tables est :

Table EMP :

EMPNOENAMEJOBMGRHIREDATESALCOMMDEPTNO
7369SMITHCLERK790217/12/198080020
7876ADAMSCLERK778823/05/1987110020
7521WARDSALESMAN769822/02/1981125050030
7654MARTINSALESMAN769828/09/19811250140030
7934MILLERCLERK778223/01/1982130010
7844TURNERSALESMAN769808/09/19811500030
7499ALLENSALESMAN769820/02/1981160030030
7782CLARKMANAGER783909/06/1981245010
7698BLAKEMANAGER783901/05/1981285030
7566JONESMANAGER783902/04/1981297520
7902FORDANALYST756603/12/1981300020
7788SCOTTANALYST756619/04/1987300020
7839KINGPRESIDENT17/11/1981500010

Table DEPT:

DEPTNODNAMELOC
10ACCOUNTINGNEW YORK
20RESEARCHDALLAS
30SALESCHICAGO
40OPERATIONSBOSTON

Exécutons maintenant le produit cartésien de ces deux tables :



SELECT
EMP.EMPNO, EMP.ENAME, EMP.HIREDATE, EMP.DEPTNO, DEPT.DEPTNO, DEPT.DNAME, DEPT.LOC
FROM EMP, DEPT;

Le résultat sera :

EMPNOENAMEHIREDATEDEPTNODEPTNO_1DNAMELOC
7369SMITH17/12/19802010ACCOUNTINGNEW YORK
7499ALLEN20/02/19813010ACCOUNTINGNEW YORK
7521WARD22/02/19813010ACCOUNTINGNEW YORK
7566JONES02/04/19812010ACCOUNTINGNEW YORK
7654MARTIN28/09/19813010ACCOUNTINGNEW YORK
7698BLAKE01/05/19813010ACCOUNTINGNEW YORK
7782CLARK09/06/19811010ACCOUNTINGNEW YORK
7788SCOTT19/04/19872010ACCOUNTINGNEW YORK
7839KING17/11/19811010ACCOUNTINGNEW YORK
7844TURNER08/09/19813010ACCOUNTINGNEW YORK
7876ADAMS23/05/19872010ACCOUNTINGNEW YORK
7902FORD03/12/19812010ACCOUNTINGNEW YORK
7934MILLER23/01/19821010ACCOUNTINGNEW YORK
7369SMITH17/12/19802020RESEARCHDALLAS
7499ALLEN20/02/19813020RESEARCHDALLAS
7521WARD22/02/19813020RESEARCHDALLAS
7566JONES02/04/19812020RESEARCHDALLAS
7654MARTIN28/09/19813020RESEARCHDALLAS
7698BLAKE01/05/19813020RESEARCHDALLAS
7782CLARK09/06/19811020RESEARCHDALLAS
7788SCOTT19/04/19872020RESEARCHDALLAS
7839KING17/11/19811020RESEARCHDALLAS
7844TURNER08/09/19813020RESEARCHDALLAS
7876ADAMS23/05/19872020RESEARCHDALLAS
7902FORD03/12/19812020RESEARCHDALLAS
7934MILLER23/01/19821020RESEARCHDALLAS
7369SMITH17/12/19802030SALESCHICAGO
7499ALLEN20/02/19813030SALESCHICAGO
7521WARD22/02/19813030SALESCHICAGO
7566JONES02/04/19812030SALESCHICAGO
7654MARTIN28/09/19813030SALESCHICAGO
7698BLAKE01/05/19813030SALESCHICAGO
7782CLARK09/06/19811030SALESCHICAGO
7788SCOTT19/04/19872030SALESCHICAGO
7839KING17/11/19811030SALESCHICAGO
7844TURNER08/09/19813030SALESCHICAGO
7876ADAMS23/05/19872030SALESCHICAGO
7902FORD03/12/19812030SALESCHICAGO
7934MILLER23/01/19821030SALESCHICAGO
7369SMITH17/12/19802040OPERATIONSBOSTON
7499ALLEN20/02/19813040OPERATIONSBOSTON
7521WARD22/02/19813040OPERATIONSBOSTON
7566JONES02/04/19812040OPERATIONSBOSTON
7654MARTIN28/09/19813040OPERATIONSBOSTON
7698BLAKE01/05/19813040OPERATIONSBOSTON
7782CLARK09/06/19811040OPERATIONSBOSTON
7788SCOTT19/04/19872040OPERATIONSBOSTON
7839KING17/11/19811040OPERATIONSBOSTON
7844TURNER08/09/19813040OPERATIONSBOSTON
7876ADAMS23/05/19872040OPERATIONSBOSTON
7902FORD03/12/19812040OPERATIONSBOSTON
7934MILLER23/01/19821040OPERATIONSBOSTON

Vous verrez que le résultat affiché est l’ensemble des couples composés par les lignes des deux tables.

Dans les cas pratiques, on utilise très rarement ce genre de jointure.

  • table1.id = table2.id

Ce genre de jointure est le plus utilisé. Prenons les mêmes tables déjà utilisé ci-dessus :



SELECT
EMP.EMPNO, EMP.ENAME, EMP.HIREDATE, EMP.DEPTNO, DEPT.DEPTNO, DEPT.DNAME, DEPT.LOC
FROM EMP, DEPT
WHERE EMP.deptno = DEPT.deptno;

Cette jointure est réalisée entre les deux tables EMP et SAL. Généralement les jointures se font à travers les clés étrangères et primaires des tables. Dans notre cas, deptno est la clé étrangère dans la table EMP alors qu’elle clé primaire de la table SAL. Du coup, le résultat de cette requête sera :

EMPNOENAMEHIREDATEDEPTNODEPTNO_1DNAMELOC
7782CLARK09/06/19811010ACCOUNTINGNEW YORK
7839KING17/11/19811010ACCOUNTINGNEW YORK
7934MILLER23/01/19821010ACCOUNTINGNEW YORK
7566JONES02/04/19812020RESEARCHDALLAS
7788SCOTT19/04/19872020RESEARCHDALLAS
7902FORD03/12/19812020RESEARCHDALLAS
7369SMITH17/12/19802020RESEARCHDALLAS
7876ADAMS23/05/19872020RESEARCHDALLAS
7499ALLEN20/02/19813030SALESCHICAGO
7521WARD22/02/19813030SALESCHICAGO
7844TURNER08/09/19813030SALESCHICAGO
7698BLAKE01/05/19813030SALESCHICAGO
7654MARTIN28/09/19813030SALESCHICAGO

Vous pouvez constater que toutes les lignes de la table EMP ont été ramenées par la requête.  En plus, les informations relatives au département ont été affichées aussi. Vous pouvez aussi voir que les données du département 40 n’ont pas été sélectionnées puisqu’aucun employé n’appartient au département 40.

Lançant maintenant cette requête :

SELECT
EMPLOYE.EMPNO NUM_EMP, EMPLOYE.ENAME NOM_EMP, EMPLOYE.JOB POSTE_EMP, MANAGER.ENAME NOM_MANAGER, MANAGER.JOB POSTE_MANAGER, DEPT.DNAME DEPART
FROM EMP EMPLOYE, EMP MANAGER, DEPT
WHERE EMPLOYE.DEPTNO = DEPT.DEPTNO AND EMPLOYE.MGR = MANAGER.EMPNO;

Le résultat obtenu est :

NUM_EMPNOM_EMPPOSTE_EMPNOM_MANAGERPOSTE_ MANAGERDEPART
7788SCOTTANALYSTJONESMANAGERRESEARCH
7902FORDANALYSTJONESMANAGERRESEARCH
7499ALLENSALESMANBLAKEMANAGERSALES
7521WARDSALESMANBLAKEMANAGERSALES
7654MARTINSALESMANBLAKEMANAGERSALES
7844TURNERSALESMANBLAKEMANAGERSALES
7934MILLERCLERKCLARKMANAGERACCOUNTING
7876ADAMSCLERKSCOTTANALYSTRESEARCH
7698BLAKEMANAGERKINGPRESIDENTSALES
7566JONESMANAGERKINGPRESIDENTRESEARCH
7782CLARKMANAGERKINGPRESIDENTACCOUNTING
7369SMITHCLERKFORDANALYSTRESEARCH

Dans cette requête, en plus de la jointure entre les tables EMP et DEPT, nous avons ajouté une nouvelle jointure entre la table EMP et elle-même. La condition de cette dernière jointure est entre l’attribut MGR de la première table EMP (EMPLOYE) et l’attribut EMPNO de la deuxième table EMP (MANAGER). Nous avons affiché donc les num des employés, leurs noms, leurs postes, les noms de leurs managers, les postes des managers et les départements des employés.

Remarque : L’employé 7839 n’a pas a été sélectionné parce que l’attribut MNG est nul.

  • INNER JOIN

Les jointures INNER JOIN ou JOIN ont le même résultat que celle du paragraphe précédent.

Syntaxe :

SELECT
*
FROM table1
INNER JOIN table2 ON table1.id = table2.id;

Reprenons les deux requête du paragraphe précédent mais en utilisant INNER JOIN:

SELECT
EMP.EMPNO, EMP.ENAME, EMP.MGR, EMP.HIREDATE, EMP.DEPTNO, DEPT.DEPTNO, DEPT.DNAME, DEPT.LOC
FROM EMP
INNER JOIN DEPT ON EMP.deptno = DEPT.deptno;

 

SELECT
EMPLOYE.EMPNO NUM_EMP, EMPLOYE.ENAME NOM_EMP, EMPLOYE.JOB POSTE_EMP, MANAGER.ENAME NOM_MANAGER, MANAGER.JOB POSTE_MANAGER, DEPT.DNAME DEPART
FROM EMP EMPLOYE
JOIN EMP MANAGER ON EMPLOYE.MGR = MANAGER.EMPNO
JOIN DEPT ON EMPLOYE.DEPTNO = DEPT.DEPTNO;

La condition de jointure est ajoutée après ON. Nous pouvons ajouter un WHERE après avoir faire la jointure. Par exemple, nous allons ajouter dans cette dernière requête une condition pour ne sélectionner que  les employés qui ont un poste ANALYST

SELECT
EMPLOYE.EMPNO NUM_EMP, EMPLOYE.ENAME NOM_EMP, EMPLOYE.JOB POSTE_EMP, MANAGER.ENAME NOM_MANAGER, MANAGER.JOB POSTE_MANAGER, DEPT.DNAME DEPART
FROM EMP EMPLOYE
JOIN EMP MANAGER ON EMPLOYE.MGR = MANAGER.EMPNO
JOIN DEPT ON EMPLOYE.DEPTNO = DEPT.DEPTNO
WHERE EMPLOYE.JOB = 'ANALYST';

Le résultat obtenu dans ce cas est :

NUM_EMPNOM_EMPPOSTE_EMPNOM_MANAGERPOSTE_ MANAGERDEPART
7788SCOTTANALYSTJONESMANAGERRESEARCH
7902FORDANALYSTJONESMANAGERRESEARCH
  • FULL, RIGHT et LEFT JOIN (jointure externe)

Ce type de jointure externe est très intéressant. Dans notre requête qui affiche les employés et leurs Manager, une ligne n’a pas été sélectionnée. Le Manager de cette ligne est vide. Mais si on voulait avoir les données de tous les employés (qui ont ou pas un Manager) avec les données de leurs Mangers s’elles existent, la requête sera alors :

SELECT
EMPLOYE.EMPNO NUM_EMP, EMPLOYE.ENAME NOM_EMP, EMPLOYE.JOB POSTE_EMP, MANAGER.ENAME NOM_MANAGER, MANAGER.JOB POSTE_MANAGER, DEPT.DNAME DEPART
FROM EMP EMPLOYE
LEFT JOIN EMP MANAGER ON EMPLOYE.MGR = MANAGER.EMPNO
JOIN DEPT ON EMPLOYE.DEPTNO = DEPT.DEPTNO;

Le résultat est :

NUM_EMPNOM_EMPPOSTE_EMPNOM_NPLUS1POSTE_NPLUS1DEPART
7902FORDANALYSTJONESMANAGERRESEARCH
7788SCOTTANALYSTJONESMANAGERRESEARCH
7654MARTINSALESMANBLAKEMANAGERSALES
7844TURNERSALESMANBLAKEMANAGERSALES
7521WARDSALESMANBLAKEMANAGERSALES
7499ALLENSALESMANBLAKEMANAGERSALES
7934MILLERCLERKCLARKMANAGERACCOUNTING
7876ADAMSCLERKSCOTTANALYSTRESEARCH
7698BLAKEMANAGERKINGPRESIDENTSALES
7566JONESMANAGERKINGPRESIDENTRESEARCH
7782CLARKMANAGERKINGPRESIDENTACCOUNTING
7369SMITHCLERKFORDANALYSTRESEARCH
7839KINGPRESIDENTACCOUNTING

Vous pouvez voir que l’employé  7839 est sélectionné et que les attributs NOM_NPLUS1 et POSTE_NPLUS1 sont vide.

De la même manière, RIGHT JOIN a le même comportement que LEFT JOIN mais au sens contraire.

EMP EMPLOYE LEFT JOIN EMP MANAGER ON EMPLOYE.MGR = MANAGER.EMPNO est équivalent à EMP MANAGER RIGHT JOIN EMP EMPLOYE ON EMPLOYE.MGR = MANAGER.EMPNO

FULL JOIN est une jointure dans les deux sens. Pour mieux comprendre cette jointure, faisons l’exemple suivant :

Ajoutons une ligne dans la table EMP

INSERT INTO EMP VALUES (1, 'NOM', 'JOB', 7902, '01/01/1980', 1234, NULL, 60);

Exécutons la requête ci-dessous :

SELECT
EMP.EMPNO, EMP.ENAME, EMP.HIREDATE, EMP.DEPTNO, DEPT.DEPTNO, DEPT.DNAME, DEPT.LOC FROM EMP
FULL JOIN DEPT ON EMP.deptno = DEPT.deptno;

Le résultat sera

EMPNOENAMEHIREDATEDEPTNODEPTNO_1DNAMELOC
7782CLARK09/06/19811010ACCOUNTINGNEW YORK
7839KING17/11/19811010ACCOUNTINGNEW YORK
7934MILLER23/01/19821010ACCOUNTINGNEW YORK
7566JONES02/04/19812020RESEARCHDALLAS
7788SCOTT19/04/19872020RESEARCHDALLAS
7902FORD03/12/19812020RESEARCHDALLAS
7369SMITH17/12/19802020RESEARCHDALLAS
7876ADAMS23/05/19872020RESEARCHDALLAS
7499ALLEN20/02/19813030SALESCHICAGO
7521WARD22/02/19813030SALESCHICAGO
7844TURNER08/09/19813030SALESCHICAGO
7698BLAKE01/05/19813030SALESCHICAGO
7654MARTIN28/09/19813030SALESCHICAGO
1NOM01/01/198060
40OPERATIONSBOSTON

Vous pouvez constater que toutes les lignes des deux tables sont affichées même ceux qui n’ont pas d’équivalence.

Pour finir ce cours, il faut savoir que nous pouvons réaliser ces dernières jointures (FULL, RIGHT et LEFT JOIN) en utilisant les jointures ordinaires. Pour se faire, nous utilisons le symbole (+)

FULL JOIN correspond à table1.id (+) = table2.id (+)

RIGHT JOIN correspond à table1.id (+) = table2.id

LEFT JOIN correspond à table1.id = table2.id (+)

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *