1. 程式人生 > 其它 >left jon連線查詢踩坑記

left jon連線查詢踩坑記

  專案開發中經常會使用到多張表進行關聯查詢,比如left join關聯查詢。

如果有一張表A和一張表B,查詢語句 SELECT a.*,b.name from A a left join B b

On a.id = b.id 表示的含義的就是取A表獨有的資料和A表和和B表共有的資料。

如上圖所示,主表是A表,用A表去左關聯查詢B表,正常情況下會返回A

的所有資料,不管這些資料在B表中是否存在。

  自己在寫SQL語句的時候,突然發現查詢條件的位置不一樣,導致查詢結果

出現很大的差異,讓我很是疑惑。下面就來複現這個問題,首先建立兩張表AB.

A插入3條資料,沒有刪除,is_deleted = 1

表示刪除。

B插入三條資料,刪除其中兩條資料。

自己查詢的時候,想要查詢兩張表中沒有刪除的資料,於是寫了第一個查詢語句,結果如下,

自己一看這結果明顯的不對,表A是主表,會取表中的所有資料,這種查詢方式只取到一條資料。

然後換一種方式進行查詢,如下

得到了自己想要的結果,A表的所有記錄都需要,去關聯B表查詢的時候,如果匹配到就取B

的結果,如果沒匹配到就返回null。進一步改進的查詢方式為,

為了更好的比較,自己又新增一個查詢語句,把b表的是否刪除的條件去掉,查詢結果如下

  自己很好奇為什麼會出現這種狀況呢?查詢條件寫的位置不一樣,就會導致查詢結果不一致。

然後去網上尋找問題的答案,最終找到這個問題的答案:

on條件是在生成臨時表的查詢條件,不管連線的條件如何,最終都會返回主表的所有資料。

Where條件則是過濾掉臨時表的資料,即是對最終資料的過濾,如果條件不符合則就直接過濾掉。

因此

SELECT

a.*, b. NAME

FROM

table_a a

LEFT JOIN table_b b ON a.id = b.id

WHERE

a.is_deleted = 0

AND b.is_deleted = 0;

這種查詢方式就把後面兩條資料過濾掉,因為其不滿足 b.is_deleted = 0 的條件。

自己在查詢的時候,只是想使用B表的有效資料進行關聯查詢,過濾條件就不能直接寫在

Where條件中,需要寫在on後面或者是使用子查詢過濾掉。

  到此問題解決。以前寫關聯查詢的時候,不需要考慮資料是否有效都是直接進行關聯查詢,

現在遇到問題,則需要特別小心,稍微不注意就會出現意想不到的錯誤,吸取這次的深刻教訓。

參考菜鳥教程中的答案。

https://www.runoob.com/w3cnote/sql-different-on-and-where.html