1. 程式人生 > >Oracle的連線詳解(左連線、右連線、全連線...)

Oracle的連線詳解(左連線、右連線、全連線...)

1  說明:

提到資料庫必須要知道聯接操作,這部分的內容在資料庫查詢操作中佔到舉足輕重的地位,今天我就來說說這些聯結操作。

聯接操作可以在WHERE中指定,也可以在FROM子句中指定,在FROM子句中指定聯接條件時,SQL2將聯接操作符分為聯接型別和聯接條件兩部分。

聯接型別決定了如何處理聯接條件中不匹配的元組。

2  連線操作:

聯接條件決定了兩個關係中那些元素該匹配。

聯接型別

說明

INNER JOIN

內聯接,結果為兩個聯接表中的匹配行的聯接

LEFT OUTER JOIN

左聯接:結果包括左表(出現在JOIN子句最左邊)中的所有行,不包括右表中的不匹配行。

RIGHT OUTER JOIN

右聯接:結果包括右表(出現在JOIN子句最右邊)中的所有行,不包括有左表中的不匹配的行。

FULL OUTER JOIN

完全聯接:結果包括所有聯接中的所有行,不論他們是否匹配。

CROSS JOIN

交叉聯接:結果包括兩個聯接表中的所有可能的行組合。交叉連線返回的是兩個表的笛卡兒積。(Oracle不支援)

NATURAL JOIN

自然連線時在兩張表中尋找那些資料型別 和列名都相等的欄位,然後自動地將他們連線起來。

通俗的說:在左連線和右連線時都會以一張表作為基表,該表的內容會全部的顯示,然後加上兩張表匹配的內容。

        

此圖引用至:http://blog.csdn.net/caolaosanahnu/article/details/8080350

對於外連線,在Oracle中可以使用(+)來表示,使用的方式:

1、(+)操作符只可以出現在WHERE子句中,並且不可以和outer join語法同時使用。

2、當使用(+)操作符執行外連線時,如果在where子句中包含多個條件,則必須在所有的條件中都包含(+)操作符。

3、(+)操作符只能適用於列,而不能用在表示式上。

4、(+)操作符不能與or和in操作符一起使用。

5、(+)操作符只能用於實現左外連線和右外連線,而不能用於實現完全外連線。

自然連線的注意事項:

(1)   如果做自然連線的兩個表中有多個欄位都滿足有相同名稱和型別,那麼他們都會被作為連線的條件。

(2)   如果自然兩個表中僅欄位名稱相同,但是資料型別不同時,此時會返回一個錯誤。

這裡我再說明幾種連線方式,也當作一種補充知識了:

1、 Self joins自連線:

使用自連線,可以將自己表的一個映象作為另一張表來對待,進行連線後查詢出資料。

2、 Cartesian Products 笛卡爾積

當兩個表沒有連線操作時,對這兩個表進行查詢得到的資料是什麼樣的呢?是這兩個表的笛卡兒積。

3 多表連線操作

在進行多表聯合查詢時,會發現多表會進行連線操作的,而這些連線操作包括三種方式:

Hash Join(雜湊連線)、Nested Loops、Sort Merge join,對於這些連線方式的瞭解可以方便我們對於連線操作的進一步瞭解,下面進行一一介紹。

3.1  HASH JOIN(雜湊連線)

Hash Join雜湊連線主要是CBO(CBO: Cost-Based Optimization 基於代價的優化器, Oracle優化器之一,後續會進行介紹)做資料量比較大時進行連線操作比較常用的一種方式,優化器會選用兩個表中較小那個表(小一點表或者資料來源),利用連線鍵(JOIN KEY)在記憶體中建立散列表,將列資料儲存到hash列表中,然後掃描大的那個表,同樣對JOIN KEY到hash表進行匹配,找出可以匹配的值,此時注意:如果HASH表比較大,無法一次儲存到記憶體時則會分成不多個partition(段),寫入磁碟的temporary segment,此時效能會多出一次寫的代價,有可能會降低效率。

該內容主要適用於較小的表(可以放入記憶體),此時相關效能就是訪問了兩個的效能的成本總和。

可以用USE_HASH(table_name1 table_name2)提示來強制使用雜湊連線。

3.2  SORT MERGE JOIN:排序合併連線

Merge Join排序合併連線,是先將兩個關聯的表按照關聯鍵(JOIN KEY)進行排序,然後從各自排序表中抽取資料,到另一個排序表中進行匹配。

相對來說,merge join需要完成排序操作,所以消耗的效能比較多,但是當源如果已經進行了排序,其將會取得較好的效能。適用於:不等價關聯(>,<,>=,<=,<>)、HASH_JOIN_ENABLED=false等情況。

可以使用USE_MERGE(table_name1 table_name2)來強制使用排序合併連線.

3.3  NESTED LOOP:巢狀迴圈連線

Nested Loops巢狀迴圈連線,工作方式是迴圈從一張表中讀取資料(驅動表 outer table),然後訪問另一張表(被查詢表 inner table, 希望有索引)。驅動表中每一行與inner表中相應記錄進行連結(JOIN)。內表被外表驅動,外表中的每一行都會與內表進行匹配操作,所以查詢結果集最好不要太大。將資料量小的表作為查詢的驅動表(外表),可以利用ordered 來提示CBO預設的驅動表。

對於驅動表較小的情況時,巢狀迴圈連線相對比較好,同時inner表需要有效的訪問索引(index)。

使用USE_NL(table_name1 table_name2)可是強制CBO 執行巢狀迴圈連線。

4  舉例:

Oracle的兩張表:部門資訊表:DEPTINFO,使用者表:USERINFO

    

4.1  INNER JOIN連線操作:

INNER JOIN連線作為一種等值連線,其操作相當於where中的等至連線。

 

4.2  LEFT JOIN連線操作:

USERINFO 左連線DEPTINFO,結果將以USERINFO為基表,其內容將全部顯示。

 

Oracle包含了3種連線方式:分別是:

4.3  RIGHT JOIN連結操作

USERINFO右連線DEPTINFO,結果將以DEPTINFO為基表,將其內容全部顯示出來。

 

4.4  FULL OUTER JOIN連線操作:

USERINFO 全連線DEPTINFO,結果將USERINFO以及DEPTINFO的內容都顯示出來。

  

4.5  NATURAL JION自然連線

 

4.6  利用(+)來實現連線操作:

1、無(+)連線:

 

2、左(+)連線:(相當於Right Join)

 

3、右(+)連線:(相當於Left Join)

注意:不可以左右都加(+)。

4.7  Self Join 自連線以及Cartesian Products笛卡兒積

          

                   自連線                                                        笛卡兒積