在sql語句中,我們經常用到子查詢,在工作中也是非常的實用,對於子查詢做了以下幾點總結。
1. select (select ....) as 別名 from table
第一種,在from前面的(select)子查詢。這種子查詢的結果只能是單行單列的,可以傳遞from後面表的參數進去,表示查詢出來的每一行數據都是由這個查詢當做一列的。
2. select * from (select * ...) table
第二種,在from後面,這種子查詢會當做一個表來對待,可以有多行多列,行列沒有強制要求,還可以與別的表連接查詢,有一個強制要求,就是必須要寫別名。不可以傳遞參數。
3. select * from table where table.id = (select tab.id from tab.id)
第三種,在=,>,<,>=,<=,<>,!=關係運算符後面,這種子查詢的結果只能是單行單列,與關係判斷符前面的數據對比。可以傳遞參數。
4. select * from table where table.id in(select tab.id from tab)
第四種,在in,not in的後面,數據只能是單列的,可以是一行,也可以多行,還可以是null,可以傳遞參數。
5. select * from table where table.id <all(select tab.id from tab )
第五種,在any,some,all這些關鍵字後面,只能是單列的,可以是一行,也可以是多行,還可以是null,可以傳遞參數。
6. select * from table where exists(select * from tab)
第六種,在exists,not exists這些關鍵字後面,可以是多行多列,行列沒有要求,查出了數據就返回true,沒查出(也就是null)就返回false,可以傳遞參數。所有的用in做的sql都能轉成exists來做。exists效率比in要高
7. select * from table group by table.id having count(*) > (select count(tab.id) from tab)
第七種,在having 的=,>,<,>=,<=,<>,!=關係運算符後面,跟第三種是一樣的約束,這種子查詢的結果只能是單行單列,與關係判斷符前面的數據對比。可以傳遞參數。
8. select * from table where table.id like (select tab.id from tab where tab.id='1')
第八種,在like的後面,返回的值只能是單行單列,因爲要與table.id對比,只能是是單行單列,可以傳遞參數。返回的結果還能用concat(...)函數拼接。
總結:
這些經驗要經常使用,纔會記得牢固,多用纔是硬道理。
附錄一些小知識點:
some關鍵字等於any,some只是any的別名。
in 等價於 =any() , not in 等價於 <>all() 或者 !=all()。
遇到一個字段的含義要等效於全部的情況,用in做不了時(比如,求學了張三老師全部課程的學生信息)採用not exists來做,雙層否定等於肯定。
能用in來做的都可以轉換成用exists來做,而且,exists的效率比in要高。
not的位置一般都是在字段前面,表示非的意思,也就是反面,
邏輯運算符(and,or,not)
關係運算符(<>,!=,<,>,<=,>=,=),<>等價於!=