złączenie trzech tabel - składnia z "join"

0

Witam,

Proszę o wyjaśnienie zasad łączenia trzech i więcej tabel oraz składni kodu, dzięki której można to osiągnąć. Do nauki stworzyłem sobie właśnie 3 proste tabelki takimi oto poleceniami:

create database Error;

use Error;

create table Osoby
(
id_osoba int primary key auto_increment,
osoba char(20)
);

create table Kolory
(
id_kolor int primary key auto_increment,
kolor char(20) not null
);

create table Osoby_Kolory
(
	id_osoba int,
	id_kolor int
);

alter table Osoby_Kolory add constraint foreign key (id_kolor) references Kolory(id_kolor);
alter table Osoby_Kolory add constraint foreign key (id_osoba) references Osoby(id_osoba);

insert into Osoby values (NULL, 'Jacek Placek'), (NULL, 'Osiołek Matołek'), (NULL, 'Czerwony Kapturek');
insert into Kolory values (NULL, 'biały'), (NULL, 'czerwony');

insert into Osoby_Kolory values (2, 1), (3, 2);

Jak widać - pierwsza tabela zawiera osoby, druga kolory, trzecia z kolei każdej osobie przyporządkowuje kolor. I tak - Osiołek Matołek "lubi" kolor biały, Czerwony Kapturek "lubi" czerwony, natomiast Jacek Placek nie ma przyporządkowanego żadnego koloru. I ten właśnie brak przyporządkowania chciałbym uwidocznić w tabeli wynikowej za pomocą odpowiedniego polecenia. Takie polecenie:

select Osoby.osoba, Kolory.kolor from Osoby, Kolory, Osoby_Kolory where Osoby.id_osoba = Osoby_Kolory.id_osoba and Kolory.id_kolor = Osoby_Kolory.id_kolor;

pokazuje tylko pary "dopasowane", nie widać, że Jacek Placek nie ma przyporządkowanego sobie koloru. Wiem, że można coś takiego w prosty sposób osiągnąć używając składni z "left/right/full join", jednak do tej pory nie znalazłem nigdzie przystępnego wyjaśnienia tego problemu.

Tak więc proszę o pomoc i z góry dziękuję :)

1
select o.osoba, ok.id_kolor from osoby o join osoby_kolory ok on ok.id_osoba=o.id_osoba

Najprostsze połączenie tabel - takie jak ty miałeś za pomocą WHERE. Ale to nie daje wszystkich osób, tylko dopasowane.

select o.osoba, ok.id_kolor from osoby o left join osoby_kolory ok on ok.id_osoba=o.id_osoba

To już daje, bo jest LEFT JOIN. I od razu widać, że kolor jest Nullem. Może być Nullem w dwóch przypadkach - brak rekordu, lub rekord znaleiony, ale pole m fizycznie wartość Null. Aby się przekonać, czy rekord jest znaleziony musiałbyś wyświetlić wartość pola z połączenia (tego z klauzuli ON ...) - tu id_osoba.

select o.osoba, ok.id_kolor, k.kolor from osoby o left join osoby_kolory ok on ok.id_osoba=o.id_osoba left join kolory k on k.id_kolor=ok.id_kolor

Dodana trzeciaa tabela - również z LEFT JOIN. Czemu? Wykasuj, a się przekonasz... Możesz sobie doczytać czemu tak. Podpowiem: Null=Null to zdanie fałszywe

0

Przykład

SELECT Osoby.osoba, Kolory.kolor FROM
Osoby LEFT JOIN Osoby_Kolory ON Osoby_Kolory.id_osoba = Osoby.id_osoba LEFT JOIN Kolory ON Kolory.id_kolor = Osoby_Kolory.id_kolor;

rzeczywiście działa.

Nasuwa mi się jednak kolejne pytanie: dlaczego zamiast "left join" nie można by użyć "full join"?

0

FULL JOIN pokaże ci również kolory bez przypasowanej osoby. A tobie nie o to chodziło.

0

A czy mógłbyś zaprezentować tutaj wynik polecenia z full join i jego składnię? Oczywiście zakładając dodany kolor, który nie ma przyporządkowanej sobie osoby.

1 użytkowników online, w tym zalogowanych: 0, gości: 1