web-dev-qa-db-fra.com

L'ordre de jointure est-il important en SQL?

Sans tenir compte des performances, les résultats des requêtes A et B ci-dessous donneront-ils le même résultat? Que diriez-vous de C et D?

-- A
select *
from   a left join b
           on <blahblah>
       left join c
           on <blahblan>


-- B
select *
from   a left join c
           on <blahblah>
       left join b
           on <blahblan>  

-- C
select *
from   a join b
           on <blahblah>
       join c
           on <blahblan>


-- D
select *
from   a join c
           on <blahblah>
       join b
           on <blahblan>  
162
Just a learner

Pour INNER rejoint, non, l'ordre n'a pas d'importance. Les requêtes renverront les mêmes résultats, tant que vous modifiez vos sélections de SELECT * à SELECT a.*, b.*, c.*.


Pour (LEFT, RIGHT ou FULL) OUTER joint, oui, l'ordre est important - et ( mis à jour ) les choses sont beaucoup plus compliquées.

Premièrement, les jointures externes ne sont pas commutatives, donc a LEFT JOIN b n'est pas identique à b LEFT JOIN a.

Les jointures externes ne sont pas non plus associatives, donc dans vos exemples qui impliquent les deux propriétés (commutativité et associativité):

a LEFT JOIN b 
    ON b.ab_id = a.ab_id
  LEFT JOIN c
    ON c.ac_id = a.ac_id

équivaut à:

a LEFT JOIN c 
    ON c.ac_id = a.ac_id
  LEFT JOIN b
    ON b.ab_id = a.ab_id

mais:

a LEFT JOIN b 
    ON  b.ab_id = a.ab_id
  LEFT JOIN c
    ON  c.ac_id = a.ac_id
    AND c.bc_id = b.bc_id

n'est pas équivalent à:

a LEFT JOIN c 
    ON  c.ac_id = a.ac_id
  LEFT JOIN b
    ON  b.ab_id = a.ab_id
    AND b.bc_id = c.bc_id

Un autre exemple d'associativité (heureusement plus simple). Pensez à ceci comme (a LEFT JOIN b) LEFT JOIN c:

a LEFT JOIN b 
    ON b.ab_id = a.ab_id          -- AB condition
 LEFT JOIN c
    ON c.bc_id = b.bc_id          -- BC condition

Ceci est équivalent à a LEFT JOIN (b LEFT JOIN c):

a LEFT JOIN  
    b LEFT JOIN c
        ON c.bc_id = b.bc_id          -- BC condition
    ON b.ab_id = a.ab_id          -- AB condition

seulement parce que nous avons "Nice" ON conditions. ON b.ab_id = a.ab_id et c.bc_id = b.bc_id sont des contrôles d'égalité et n'impliquent pas de comparaisons NULL.

Vous pouvez même avoir des conditions avec d'autres opérateurs ou avec des opérateurs plus complexes comme: ON a.x <= b.x ou ON a.x = 7 ou ON a.x LIKE b.x ou ON (a.x, a.y) = (b.x, b.y) et les deux requêtes seraient toujours équivalentes.

Si, toutefois, l'un de ceux-ci impliquait IS NULL ou une fonction liée à des valeurs nulles telle que COALESCE(), par exemple, si la condition était b.ab_id IS NULL, les deux requêtes ne seraient pas équivalentes.

200
ypercubeᵀᴹ

pour les jointures régulières, ce n'est pas le cas. TableA join TableB produira le même plan d'exécution que TableB join TableA (vos exemples C et D seront donc les mêmes)

pour la gauche et la droite rejoint il fait. TableA left Join TableB est différent de TableB left Join TableA, MAIS c'est la même chose que TableB right Join TableA

4
Diego

Si vous essayez de rejoindre C sur un champ de B avant de rejoindre B, c’est-à-dire:

SELECT A.x, A.y, A.z FROM A 
   INNER JOIN C
       on B.x = C.x
   INNER JOIN b
       on A.x = B.x

votre requête échouera, donc dans ce cas, l'ordre est important.

0
Teo J.

optimiseur Oracle choisit l'ordre de jointure des tables pour la jointure interne. L'optimiseur choisit l'ordre de jointure des tables uniquement dans les clauses FROM simples. Vous pouvez consulter la documentation Oracle sur leur site Web. Et pour la jointure extérieure gauche, la réponse la plus votée est la bonne. L'optimiseur choisit l'ordre de jointure optimal ainsi que l'index optimal pour chaque table. L'ordre de jointure peut affecter le meilleur choix d'index. L'optimiseur peut choisir un index comme chemin d'accès pour une table s'il s'agit de la table interne, mais pas s'il s'agit de la table externe (et s'il n'y a pas d'autres qualifications).

L'optimiseur choisit l'ordre de jointure des tables uniquement dans les clauses FROM simples. La plupart des jointures utilisant le mot-clé JOIN sont transformées en jointures simples. L'optimiseur choisit donc leur ordre de jointure.

L'optimiseur ne choisit pas l'ordre de jointure pour les jointures externes; il utilise l'ordre spécifié dans l'instruction.

Lors de la sélection d'un ordre de jointure, l'optimiseur prend en compte: La taille de chaque table Les index disponibles sur chaque table Indique si un index d'une table est utile dans un ordre de jointure particulier Le nombre de lignes et de pages à analyser pour chaque table de chaque table. rejoindre l'ordre

0
Saumyojit Das