2014-06-19 224 views
1

我一直有麻煩理解這個例子,我有答案,但我有麻煩包裝我的頭周圍如何工作。聯接如何工作?SQL加入和左外部加入

檢查PLAYER和TEAM表的結構:

PLAYER 
    ------------- 
    PLAYER_ID NUMBER(9) PK 
    LAST_NAME VARCHAR2(25) 
    FIRST_NAME VARCHAR2(25) 
    TEAM_ID NUMBER 
    MANAGER_ID NUMBER(9) 

    TEAM 
    ---------- 
    TEAM_ID NUMBER PK 
    TEAM_NAME VARCHAR2(30) 

在這個例子中,團隊經理也播放器,以及MANAGER_ID列引用PLAYER_ID列。對於經理人員,MANAGER_IDNULL

哪個SELECT聲明將提供所有球員的列表,包括球員的姓名,球隊名稱和球員的經理姓名?

答:

SELECT p.last_name, p.first_name, m.last_name, m.first_name, t.team_name 
    FROM player p 
    LEFT OUTER JOIN player m ON (p.manager_id = m.player_id) 
    LEFT OUTER JOIN team t ON (p.team_id = t.team_id); 
+0

要說明這一點,最好的方法是從字面上繪製您的表格的圖片。一個在左邊,一個在右邊。箭頭指向哪個方向?這就是你的加入將起作用的方式。您將獲得「左側的所有記錄」或「右側的所有記錄」。 – durbnpoisn

回答

2

所以第一LEFT OUTER JOIN則玩家表,然後對每個球員經理信息補充道。每位球員的經理都有一個ID,他也是一名ID的球員。如果A先生,player_id 9是Ted的經理,player_id 5,那麼Ted的manager_id將是9。第一次加入需要Ted的manager_id,9,並將其與他的經理A先生的player_id相匹配,以便經理的信息現在也在桌面上,並且m.last_name和​​將顯示A先生的姓名。第二次加入需要team_id,並簡單地將其與隊伍表相匹配,將team_name附加到表中的玩家信息。

如果沒有樣本數據和圖表,很難解釋。抱歉。

+1

實際上我有這種感覺。我會再次瀏覽一遍,我想我會理解這是如何工作的。謝謝! – dood

0

更簡單的思考方法是分別查看每個joins

A Left Outer JoinJoin的一種,它在提供的配對上將兩個表連接在一起,如果存在匹配,則從右側拉取數據​​。但是,如果找不到匹配,從右邊返回的數據只是Null。這與Inner Join不同,如果找不到匹配,則簡單地省略記錄。

對於這一點,玩家可能會或可能不會有一個經理,所以它的使用Left Outer Join要麼拉回經理Player記錄,如果球員有一個經理,或者如果玩家沒有,它會返回Null

同樣,玩家可能會或可能不會是一個團隊,所以它是Left Outer Join荷蘭國際集團的Team表拉回Team信息,如果玩家是一個團隊,否則這將是Null

Select聲明只是簡單地從三個表中選擇想要顯示的字段。

不同類型的Join S的一個很好的例子可以看這裏:Difference Between Inner and Outer Joins

3

在你的榜樣,同時也是管理者的球員,在的manager_id列空值。就拿SQL語句,它是第一部分:

SELECT p.last_name, p.first_name, m.last_name, m.first_name, t.team_name 
FROM player p 
LEFT OUTER JOIN player m ON (p.manager_id = m.player_id) 

既然你執行的是LEFT JOIN(而不是INNER JOIN),你的經理記錄不會被過濾掉(即使在他們的NULL值manager_id列將不會成功加入player表中的任何player_id),並且m.last_name和m.first_name對於這些管理員玩家將爲NULL。

如果您要將查詢更改爲INNER JOIN,那麼您的管理員的球員根本不會被查詢返回,因爲他們對於manager_id具有NULL值,並且沒有player_id的球員記錄的NULL。

SELECT p.last_name, p.first_name, m.last_name, m.first_name, t.team_name 
FROM player p 
INNER JOIN player m ON (p.manager_id = m.player_id) 

我希望這有助於!

+0

啊我明白了。內部聯接只會返回所有沒有經理的球員。 LEFT OUTER將返回所有球員和經理。 – dood

+1

你明白了!起初很難想象,我真的在這個概念上掙扎了很長時間。 – MDiesel