====== [SQL] Full Outer Join ======
MySQl Unterstützt keine FULL OUTER JOIN. Es gibt verschiedene Ansätze wie man das lösen kann. Sehr
verbreitet ist die Version mit einem UNION über einen LEFT und einen RIGHT OUTER JOIN.
===== Beispieldaten =====
Für meine Beispiele habe ich mal 2 Tabellen erstellet. foj1 - 3.
CREATE TABLE `foj1` (
`id` BIGINT(20) NOT NULL DEFAULT '0',
`v1` INT(10) NULL DEFAULT NULL
)
INSERT INTO `foj1` (`id`, `v1`) VALUES (1, 11);
INSERT INTO `foj1` (`id`, `v1`) VALUES (2, 12);
INSERT INTO `foj1` (`id`, `v1`) VALUES (3, 13);
CREATE TABLE `foj2` (
`id` BIGINT(20) NOT NULL DEFAULT '0',
`v2` INT(10) NULL DEFAULT NULL
)
INSERT INTO `foj2` (`id`, `v2`) VALUES (1, 21);
INSERT INTO `foj2` (`id`, `v2`) VALUES (3, 23);
INSERT INTO `foj2` (`id`, `v2`) VALUES (4, 24);
CREATE TABLE `foj3` (
`id` BIGINT(20) NOT NULL DEFAULT '0',
`v3` INT(10) NULL DEFAULT NULL
)
INSERT INTO `foj3` (`id`, `v3`) VALUES (3, 33);
INSERT INTO `foj3` (`id`, `v3`) VALUES (5, 35);
So sehen dann die Tabellen aus
^ foj1 ^^
^ id ^ v1 ^
| 1 | 11 |
| 2 | 12 |
| 3 | 13 |
^ foj2 ^^
^ id ^ v2 ^
| 1 | 21 |
| 3 | 23 |
| 4 | 24 |
^ foj3 ^^
^ id ^ v3 ^
| 3 | 33 |
| 5 | 35 |
===== Lösung mit LEFT OUTER JOIN UNION RIGHT OUTER JOIN =====
==== Über 2 Tabellen ====
SELECT f1.id, f1.v1, f2.v2
FROM foj1 f1 LEFT JOIN foj2 f2 ON f1.id = f2.id
UNION
SELECT f2.id, f1.v1, f2.v2
FROM foj1 f1 RIGHT JOIN foj2 f2 ON f1.id = f2.id
^ id ^ v1 ^ v2 ^
| 1 | 11 | 21 |
| 2 | 12 | _NULL_ |
| 3 | 13 | 23 |
| 4 | _NULL_ | 24 |
==== Über 3 Tabellen ====
Soweit so gut. Aber wenn man mehrere Tabellen zusammensetzen will, wird das schnell mal sehr unübersichtlich.
SELECT a.id, a.v1, a.v2, f3.v3
FROM
(
SELECT f1.id, f1.v1, f2.v2
FROM foj1 f1 LEFT JOIN foj2 f2 ON f1.id = f2.id
UNION
SELECT f2.id, f1.v1, f2.v2
FROM foj1 f1 RIGHT JOIN foj2 f2 ON f1.id = f2.id
) a
LEFT JOIN foj3 f3 ON a.id = f3.id
UNION
SELECT f3.id, b.v1, b.v2, f3.v3
FROM
(
SELECT f1.id, f1.v1, f2.v2
FROM foj1 f1 LEFT JOIN foj2 f2 ON f1.id = f2.id
UNION
SELECT f2.id, f1.v1, f2.v2
FROM foj1 f1 RIGHT JOIN foj2 f2 ON f1.id = f2.id
) b
RIGHT JOIN foj3 f3 ON b.id = f3.id
^ id ^ v1 ^ v2 ^ v3 ^
| 1 | 11 | 21 | _NULL_ |
| 2 | 12 | _NULL_ | _NULL_ |
| 3 | 13 | 23 | 33 |
| 4 | _NULL_ | 24 | _NULL_ |
| 5 | _NULL_ | _NULL_ | 35 |
===== Lösung über gemeinsamer Key =====
Wenn alle 3 Tabellen über denselben Schlüssel verknüpft sind, kann man es vereinfachen
Dazu nehmen wir mit einem UNION von allen Tabellen die ID und erstellen uns so mal ein Datensatz
auf den wir die Tabellen wieder mittels LEFT JOIN anhängen können
SELECT
ids.id,
foj1.v1,
foj2.v2,
foj3.v3
FROM
(
-- Alle ids ausfindig machen
SELECT DISTINCT id FROM foj1
UNION DISTINCT SELECT id FROM foj2
UNION DISTINCT SELECT id FROM foj3
) AS ids
-- und die Daten dazu verknüpfen
LEFT JOIN foj1 ON ids.id = foj1.id
LEFT JOIN foj2 ON ids.id = foj2.id
LEFT JOIN foj3 ON ids.id = foj3.id
^ id ^ v1 ^ v2 ^ v3 ^
| 1 | 11 | 21 | _NULL_ |
| 2 | 12 | _NULL_ | _NULL_ |
| 3 | 13 | 23 | 33 |
| 4 | _NULL_ | 24 | _NULL_ |
| 5 | _NULL_ | _NULL_ | 35 |
{{tag>MySQL}}