2014-01-17 77 views
6

我今天打錯了一個查詢,但它仍然工作,並給出了預期的結果。我的意思是運行此查詢:WHERE子句或ON子句中的INNER JOIN條件?

SELECT e.id FROM employees e JOIN users u ON u.email=e.email WHERE u.id='139840' 

,但我不小心碰到這個查詢

SELECT e.id FROM employees e JOIN users u ON u.email=e.email AND u.id='139840' 

(注意的AND代替WHERE最後子句中)

兩者返回正確的員工ID來自用戶ID。

這2個查詢有什麼區別?第二種形式是否只加入滿足條件的兩個表中的成員,而第一種形式會加入整個表,然後運行查詢?一個或多或少比另一個更有效率?我錯過了什麼嗎?

謝謝!

+3

查詢優化器可能將它們視爲等同,因爲它們具有相同的含義... –

+1

如果你切換到'LEFT OUTER JOIN',那麼只有第二次woud work'如預期' – Strawberry

+0

[INNER JOIN ON vs WHERE子句]的可能重複(http://stackoverflow.com/questions/1018822/inner-join-on-vs-where-條款) –

回答

4

對於這樣的內部連接,它們在邏輯上是等效的。但是,您可以運行到連接子句中的條件與where子句中的條件不同的情況。

作爲一個簡單的例子,假設你做了這樣的左連接;

select x.id 
from x 
     left join y 
     on x.id = y.id 
; 

這裏我們取所有來自x的行,不管y中是否有匹配的id。現在讓我們來說說我們的連接條件增長 - 我們不僅僅是根據id來查找y中的匹配,而且還會根據id_type查找匹配。

select x.id 
from x 
     left join y 
     on x.id = y.id 
     and y.id_type = 'some type' 
; 

再次,這給出了x中的所有行,無論y中是否存在匹配(id,id_type)。

這是非常不同的,雖然:

select x.id 
from x 
     left join y 
     on x.id = y.id 
where y.id_type = 'some type' 
; 

在這種情況下,我們正在採摘x的所有行,並試圖從y中匹配的行。現在,對於y中沒有匹配的行,y.id_type將爲空。因此,y.id_type ='some type'不滿足,所以那些沒有匹配的行將被丟棄,這有效地將其轉換爲內部聯接。長話短說:對於內部連接,條件轉到哪裏並不重要,但對於外部連接它可以。

3

對於INNER JOIN,這兩個查詢在語義上是相同的,這意味着它們保證具有相同的結果。如果您使用的是外部連接,那麼這兩個查詢的含義可能會非常不同,結果也會不同。

表現明智,我會期望這兩個查詢會導致相同的執行計劃。但是,查詢引擎可能會讓你感到驚訝。要知道的唯一方法是查看兩個查詢的執行計劃。

2

如果它是一個外部聯接而不是內部聯接,會得到意想不到的結果,但是在使用內部聯接時,使用其他聯接條件而不是WHERE子句並沒有真正的區別。

從表現上看,它們很可能是相同的,但不能確定。

4

優化器會將它們視爲相同。你可以做一個解釋來證明你自己。

因此,寫一個更清晰。

SELECT e.id 
FROM employees e JOIN users u ON u.email=e.email 
WHERE u.id='139840' 
1

我帶着我的團隊在工作中的同事。這個響應是以SQL Server爲中心的,而不是MySQL。但是,優化程序應該在SQL和MySQL之間有相似的操作。

一些想法: 本質上,如果您必須添加WHERE,還會執行額外的表掃描來驗證每個條件的相等性一個OR與數據集的一個數量級,一個OR,這個決定是在第一個真實條件下進行的) - 如果您在示例中有一個id指針,則反之極其快速,如果您必須查找屬於所有記錄的屬性對於一個公司或部門來說,它會變得更加模糊,因爲你可能有多個記錄。如果您可以應用等於條件,那麼在使用具有大量行的AuditLog或EventLog表時,它會更加有效。人們不會在小桌子上看到這樣的巨大好處(大約200,000行左右)。

來源:Allesandro卑 http://suxstellino.wordpress.com/2013/01/07/sql-server-logical-query-processing-summary/

來源:伊茨克奔甘 http://tsql.solidq.com/books/insidetsql2008/Logical%20Query%20Processing%20Poster.pdf