Оставлено ли соединение коммутативным? Каковы его свойства?

Предположим, таблицы TableATableBTableC а также TableD:

Это следующий запрос:

TableA INNER JOIN TableB LEFT JOIN TableC LEFT JOIN TableD

(все соединены в столбце id) эквивалентно:

TableA INNER JOIN TableB
     INNER JOIN TableC
     LEFT JOIN TableD    

UNION  

TableA INNER JOIN TableB
    LEFT JOIN TableC ON TableB.c_id IS NULL
    LEFT JOIN TableD    

?

Замечания:
Или вместо союза просто сделай

TableA INNER JOIN TableB
       INNER JOIN TableC
        LEFT JOIN TableD  

А потом

TableA INNER JOIN TableB
       LEFT JOIN TableC ON TableB.c_id IS NULL
       LEFT JOIN TableD    

а затем объединить результаты

Обновить
Является

(A INNER JOIN B) LEFT JOIN C LEFT JOIN D 

такой же как:

A INNER JOIN (B LEFT JOIN C) LEFT JOIN D

?

1 ответ

Википедия:

"В математике двоичная операция является коммутативной, если изменение порядка операндов не меняет результат. Это фундаментальное свойство многих двоичных операций, и от этого зависит множество математических доказательств".

Ответ:

нет, левое соединение не коммутативно. И внутреннее соединение есть.

Но это не совсем то, что вы просите.

Это следующий запрос:

TableA INNER JOIN TableB LEFT JOIN TableC LEFT JOIN TableD

(все соединены в столбце id) эквивалентно:

TableA INNER JOIN TableB
       INNER JOIN TableC
        LEFT JOIN TableD   
UNION     
TableA INNER JOIN TableB
        LEFT JOIN TableC ON TableB.c_id IS NULL
        LEFT JOIN TableD    

Ответ:

Тоже нет. Вообще говоря, союзы и объединения не делают одно и то же. В некоторых случаях вы можете написать их эквивалентным образом, но я не думаю, что такое общее псевдо sql вы показываете. Конституция ON, похоже, не должна работать (может быть, то, о чем я не знаю в MySQL?)

Вот упрощенный набор запросов, который я считаю эквивалентным.

SELECT * 
  FROM TableA a 
       LEFT JOIN 
       TableB b ON a.id = b.id_a 

SELECT * 
  FROM TableA a 
       INNER JOIN 
       TableB b ON a.id = b.id_a 
UNION      
SELECT * 
  FROM TableA a  
       LEFT JOIN 
       TableB b ON a.id = b.id_a 
 WHERE TableB.id IS NULL

Изменить 2:

Вот еще один пример, который ближе к вашему, но по сути тот же.

SELECT * 
  FROM            TableA a 
       INNER JOIN TableB b ON a.id = b.id_a 
        LEFT JOIN TableC c ON b.id = c.id_b 

такой же как

SELECT * 
  FROM TableA a 
       INNER JOIN TableB b ON a.id = b.id_a 
       INNER JOIN TableC c ON b.id = c.id_b 
UNION      
SELECT * 
  FROM TableA a  
       INNER JOIN TableB b ON a.id = b.id_a 
        LEFT JOIN TableC c ON b.id = c.id_b 
 WHERE TableC.id IS NULL

Но я все еще не думаю, что отвечаю на ваш настоящий вопрос.

Другие вопросы по тегам