首先准備了兩個表 (Student 和 Course),其中 Student 表中的 C_S_Id 字段為外鍵列,關聯的是 Course 表的 C_Id 主鍵列。
內連接(inner join):滿足on條件表達式,內連接是取滿足條件表達式的兩個表的交集(即兩個表都有的數據)。
1 select * from Student s 2 inner join Course c on s.C_S_Id=c.C_Id
外連接(outer join)分為:左外連接(left join / left outer join)、右外連接(right join / right outer join)和全外連接(full join / full outer join)
左外連接(left join / left outer join): 滿足on條件表達式,左外連接是以左表為准,返回左表所有的數據,與右表匹配的則有值,沒有匹配的則以空(null)取代。
1 select * from Student s 2 left join Course c on s.C_S_Id=c.C_Id
右外連接(right join / right outer join):滿足on條件表達式,右外連接是以右表為准,返回右表所有的數據,與左表匹配的則有值,沒有匹配的則以空(null)取代。
1 select * from Student s 2 right join Course c on s.C_S_Id=c.C_Id
全外連接(full join / full outer join):滿足on條件表達式,返回兩個表符合條件的所有行,a表沒有匹配的則a表的列返回null,b表沒有匹配的則b表的列返回null,即返回的是左連接和右連接的並集。
1 select * from Student s 2 full join Course c on s.C_S_Id=c.C_Id
交叉連接(cross join):交叉連接將會返回被連接的兩個表的笛卡爾積,返回結果的行數等於兩個表行數的乘積。
不加條件返回兩個表行數的乘積:
1 select * from Student s 2 cross join Course c
加上條件返回滿足條件表達式的兩個表的行:
1 select * from Student s 2 cross join Course c 3 where s.C_S_Id=c.C_Id
PS:cross join后加條件只能用where,不能用on,這一點跟后面的自連接一樣。
自連接:自連接,連接的兩個表都是同一個表,即自己連接自己。
1 -- 查詢出男生身高比女生身高矮的學生信息 2 select s1.S_Name,s1.S_Sex,s1.S_Height,s2.S_Name,s2.S_Sex,s2.S_Height 3 from Student s1, 4 Student s2 5 where s1.S_BirthDate=s2.S_BirthDate 6 and s1.S_Height<s2.S_Height 7 and s1.S_Sex='男' 8 and s2.S_Sex='女'
1 --查詢出學生身高一樣但是學號不一樣的學生信息 2 select * from Student s1,Student s2 3 where s1.S_Height=s2.S_Height 4 and s1.S_StuNo<>s2.S_StuNo
由於表的數據的原因,所以自連接的示例可能不太容易理解。可以看下面這個示例,根據表名查詢出表的主外鍵約束名,示例如下:
1 select a.Name as 表名,b.Xtype as 鍵類型,b.Name as 鍵名 2 from sysobjects a,sysobjects b 3 where a.ID=b.parent_obj and a.name='Student' 4 and b.Xtype in('F','PK')
內連接如果沒有指定連接條件的話,和笛卡爾積的交叉連接結果一樣,但是不同於笛卡爾積的地方是,沒有笛卡爾積那么復雜要先生成行數乘積的數據表,內連接的效率要高於笛卡爾積的交叉連接。
最后說明一下,交叉連接如果有WHERE子句的話,往往會先生成兩個表行數乘積的行的數據表然后再根據WHERE條件從中選擇。
因此,如果兩個表數據量太大,將會非常非常慢,不建議使用。