Je vérifie quelques anciennes instructions SQL dans le but de les documenter et de les améliorer.
Le SGBD est Oracle
Je n'ai pas compris une déclaration qui se lit comme ceci:
select ...
from a,b
where a.id=b.id(+)
Je suis confus à propos de l'opérateur (+)
et je ne l'ai pas trouvé sur aucun forum ... (la recherche de + entre guillemets n'a pas fonctionné non plus).
Quoi qu'il en soit, j'ai utilisé 'Explain Plan' de SQLDeveloper et j'ai obtenu une sortie disant que HASH JOIN, RIGHT OUTER
, etc.
Y aurait-il une différence si je supprime l'opérateur (+)
à la fin de la requête? Est-ce que la base de données doit remplir certaines conditions (comme avoir des index, etc.) avant que (+)
ne puisse être utilisé? Ce serait très utile si vous pouviez me fournir une compréhension simple ou de bons liens pour en savoir plus à ce sujet.
Merci!
C'est la notation spécifique à Oracle pour une OUTER JOIN, car le format ANSI-89 (utilisant une virgule dans la clause FROM pour séparer les références de table) ne standardise pas les jointures OUTER.
La requête serait réécrite dans la syntaxe ANSI-92 comme suit:
SELECT ...
FROM a
LEFT JOIN b ON b.id = a.id
Ce lien explique très bien la différence entre les JOIN .
Il convient également de noter que même si le (+)
fonctionne, Oracle recommande de ne pas l’utiliser :
Oracle vous recommande d'utiliser la syntaxe
FROM
clauseOUTER JOIN
plutôt que l'opérateur de jointure Oracle. Les requêtes de jointure externes qui utilisent l'opérateur de jointure Oracle(+)
sont soumises aux règles et restrictions suivantes, qui ne s'appliquent pas à la syntaxeFROM
clauseOUTER JOIN
:
L'opérateur (+) indique une jointure externe. Cela signifie qu'Oracle renverra toujours des enregistrements de l'autre côté de la jointure, même en l'absence de correspondance. Par exemple, si a et b sont emp et dpt et que vous pouvez affecter des employés à un service, l'instruction suivante renvoie les détails de tous les employés, qu'ils aient été affectés à un service ou non.
select * from emp, dept where emp.dept_id=dept.dept_id(+)
En bref, supprimer le (+) peut faire toute la différence, mais vous ne remarquerez peut-être pas longtemps, en fonction de vos données!
Dans Oracle, (+) désigne la table "facultative" dans la jointure. Donc, dans votre requête,
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a,b
WHERE a.id=b.id(+)
c'est une jointure gauche de la table 'b' à la table 'a'. Il renverra toutes les données de la table 'a' sans perdre ses données lorsque l'autre côté (la table optionnelle 'b') ne contient aucune donnée.
La syntaxe standard moderne pour la même requête serait
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a
LEFT JOIN b ON a.id=b.id
ou avec un raccourci pour a.id=b.id
(non supporté par toutes les bases de données):
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a
LEFT JOIN b USING(id)
Ancienne syntaxe, à la fois dans Oracle et dans d'autres bases de données:
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a,b
WHERE a.id=b.id
Syntaxe plus moderne:
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a
INNER JOIN b ON a.id=b.id
Ou simplement:
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a
JOIN b ON a.id=b.id
Il ne renverra que toutes les données où la valeur 'id' des tables 'a' & 'b' est la même, ce qui signifie partie commune.
Ceci est identique à une jointure gauche, mais la table est optionnelle.
Ancienne syntaxe Oracle:
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a,b
WHERE a.id(+)=b.id
Syntaxe standard moderne:
SELECT a.id, b.id, a.col_2, b.col_2, ...
FROM a
RIGHT JOIN b ON a.id=b.id
https://asktom.Oracle.com/pls/asktom/f?p=100:11:::::P11_QUESTION_ID:6585774577187
Jointure externe gauche utilisant le signe + dans Oracle 11g
En pratique, le symbole + est placé directement dans l'instruction conditionnelle et sur le côté de la table facultative (celle qui est autorisée à contenir des valeurs vides ou nulles dans la conditionnelle).