[英]Left join - two tables with the same data
可以說我有兩個帶有以下列和數據的簡單表:
Table 1 Table 2
year month year month
2017 01 2017 01
2016 12 2016 12
主鍵是由年和月組成的組合鍵。
因此,經典的左聯接為我提供了左表中的所有數據以及右表中的匹配行。
如果我像這樣左連接:
select
t1.year, t2.month
from
table1 t1
left join table 2 t2 on (t1.year = t2.year and t1.month = t2.month)
為什么我只有兩行? 我不應該得到4行嗎?
Tnx,湯姆
傳統的左聯接將為您提供“左表”中的行數(從中輸入)乘以“右表”中的匹配數(在這種情況下為LEFT JOIN
中的行),再加上所有行LEFT表中的第一個表中沒有匹配項。
2 x 1 + 0 = 2
編輯:實際上,乘法是為每一行給出的。 會像
總和(row_i xmatches_i)+不匹配
其中row_i表示每一行,而matchs_i表示第一個表中第i行的匹配項。 與此不同的是,每行可以有不同數量的匹配項(以前的公式僅適用於您的情況)
這將導致
1(行1)x 1(與第1行匹配)+ 1(行2)x 1(與第2行匹配)+ 0(表1中不匹配的行)=結果
1x1 + 1x1 + 0 =結果
1 + 1 = 2 =結果
如果您預期有4行,那么您可能想要獲得笛卡爾積。 如評論所述,在這種情況下,您可以使用交叉聯接
將表連接在一起時,實際上是在要求數據庫合並來自兩個不同表的數據並將其顯示為單個記錄。 當執行left join
,您會說:
給我表1中的所有行,以及表2中的任何關聯數據(如果存在)。
在這種意義上,表2中的數據並不代表表1的單獨或附加記錄(即使它們作為單獨的記錄存儲在單獨的表中),也代表關聯的數據。 您正在鏈接表之間的數據,而不是在每個表中追加行。
想象一下,表1存儲了人員,表2存儲了電話號碼。
Table1 Table2
+------+-------+--------+ +------+-------+-------------+
| Year | Month | Person | | Year | Month | Phone |
+------+-------+--------+ +------+-------+-------------+
| 2017 | 12 | Bob | | 2017 | 12 | 555-123-4567|
| 2016 | 01 | Frank | | 2016 | 01 | 555-234-5678|
+------+-------+-------+ +------+-------+--------------+
您可以將他們加入一起以獲得人員列表及其相應的電話號碼。 但是您不會期望從每個表中得到行的組合(兩人和兩行電話)。
您將獲得兩行,因為兩列都具有與sam及其組合鍵完全匹配的2行。 如果每行中有4行,將以相同的方式進行操作,總共只有4行。
cross join
通過組合每個參數的一行來返回您可以進行的每一行。 ( inner
) join on
從cross join
返回滿足其條件的行。 即( inner
) join on
返回您可以創建的每一行,該行合並了每個參數的一行並滿足其條件。
left join on
收益從(行inner
) join on
再加上你可以通過延長未連接的左參數行作出的行null
的右參數列。
請注意,這與主鍵,唯一列集,外鍵或任何其他約束無關 。
這里每個參數有2行,因此cross join
聯接中有2 X 2 = 4行。 但是只有2個滿足條件-行與自身結合在一起的條件。
(如果您將表與自身left join
在一起,而條件是一列的左右版本的一個或多個相等性的合計,並且這些列中沒有null
,則每個左參數行至少與自身相連接右參數。因此,沒有不連接的左參數行。因此,僅返回( inner
) join on
的行。)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.