日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

SQL基础系列(五)——子查询

發(fā)布時間:2023/12/20 数据库 26 豆豆
生活随笔 收集整理的這篇文章主要介紹了 SQL基础系列(五)——子查询 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

子查詢是在一個完整的查詢語句中,嵌套不同功能的小查詢,從而完成復雜查詢的一種編寫形式。本部分主要介紹非關聯(lián)子查詢,關聯(lián)子查詢的適用場景,語句寫法,執(zhí)行邏輯及相對應的注意事項。

目錄

1.非關聯(lián)子查詢

1.1執(zhí)行邏輯

1.2在WHERE子句中使用子查詢

1.2.1子查詢返回一個具體數(shù)據(jù)

1.2.2子查詢返回一條數(shù)據(jù)

1.2.3子查詢返回多行單列數(shù)據(jù)

1.3在HAVING子句中使用子查詢

1.4在FROM子句中使用子查詢

2.關聯(lián)子查詢

2.1在細分的組內進行比較

2.2使用EXISTS,NOT EXISTS時使用關聯(lián)子查詢


1.非關聯(lián)子查詢

在SELECT子句、GROUP BY子句、HAVING子句、ORDER BY子句中均可使用子查詢語句,較常用的是WHERE子句、HAVING子句和FROM子句。

1.1執(zhí)行邏輯

在非關聯(lián)子查詢中,子查詢語句可以獨立執(zhí)行,查詢結果是一個數(shù)據(jù),一條數(shù)據(jù),或者一張臨時數(shù)據(jù)表,主查詢可使用子查詢結果進行操作。

1.2在WHERE子句中使用子查詢

在WHERE子句中,通常使用子查詢結果作為篩選條件。

1.2.1子查詢返回一個具體數(shù)據(jù)

題目1:求table表中工資高于平均工資的數(shù)據(jù)。

在WHERE子句中不可以使用函數(shù),因此想要求大于某個統(tǒng)計值的數(shù)據(jù),不能使用如下寫法:

🙅SELECT * FROM table WHERE salary>avg(salary);

正確的示例如下:

🙆SELECT * FROM table WHERE salary>(SELECT?avg(salary) FROM table);

在上面標紅的子查詢語句中,返回結果是一個平均值,主查詢語句在執(zhí)行時判斷平均工資是否大于平均值,符合條件則作為查詢結果展示。

題目2:求table1表中和'ELLEN'職位一樣的數(shù)據(jù)

思路同上,使用子查詢語句求出'ELLEN'的職位,再將其作為篩選條件,判斷職位與其一致的數(shù)據(jù)。

🙆SELECT * FROM table1

? ? ? WHERE job=(SELECT job FROM table1 WHERE name='ELLEN');

注釋:

  • 在WHERE子句中可使用多個子查詢,支持多個條件中分別使用子查詢語句;
  • 子查詢語句可以進行嵌套;?

1.2.2子查詢返回一條數(shù)據(jù)

子查詢返回一條數(shù)據(jù),即多個屬性,使用多個屬性值進行數(shù)據(jù)判斷,示例如下:

?題目1:求table表中與'ELLEN'工作及工資均一致的數(shù)據(jù)。

題目解析:先找出'ELLEN'的工作及工資,然后判斷數(shù)據(jù)中同時和這兩個屬性一致的數(shù)據(jù)。

🙆SELECT * FROM table1

? ? ? WHERE (job,salary)=(SELECT job,salary?FROM table1 WHERE name='ELLEN');

語句返回的結果中包含ELLEN及與其工作和工資一致的數(shù)據(jù)。

1.2.3子查詢返回多行單列數(shù)據(jù)

此種情況下,子查詢返回多數(shù)據(jù)時一個數(shù)據(jù)的范圍,在WHERE子句中通過數(shù)據(jù)范圍進行篩選時,需用操作符IN、ANY、ALL

(1)IN

題目1:求每個部門最低工資,并查找出與最低工資相同的員工信息

🙆SELECT * FROM table1

? ? ? WHERE sal IN (SELECT min(sal) FROM?table1 GROUP BY deptno);

子查詢中返回的是每個部門的最低工資,一列多行。根據(jù)子查詢的結果,判斷工資在子查詢數(shù)據(jù)范圍內的數(shù)據(jù)。

??:IN,或者NOT IN 后的數(shù)據(jù)范圍內存在值為NULL的數(shù)據(jù),則查詢結果為空。

(2)ANY

題目1:求每個部門最低工資,并查找出大于任意一個部門最低工資的員工信息

🙆SELECT * FROM table1

? ? ? WHERE sal?>ANY?(SELECT min(sal) FROM?table1 GROUP BY deptno);

>ANY:大于其后數(shù)據(jù)范圍內最小值

<ANY:小于其后數(shù)據(jù)范圍內最大值

=ANY:效果相當于IN

<>ANY:🙅錯誤用法?

(3)ALL

題目1:求每個部門最低工資,并查找出比所有部門最低工資都大的員工信息

🙆SELECT * FROM table1

? ? ? WHERE sal?>ALL?(SELECT min(sal) FROM?table1 GROUP BY deptno);

<>ALL:相當于NOT IN

>ALL:大于其后數(shù)據(jù)范圍內的最大值

<ALL:小于其后數(shù)據(jù)范圍內的最小值

=ALL:🙅錯誤用法

1.3在HAVING子句中使用子查詢

在HAVING子句中使用子查詢,即對分組進行過濾,子查詢往往返回的都是一個具體的數(shù)據(jù)(單行單列)。

題目:篩選出平均工資大于全體員工平均工資的部門

🙆SELECT deptno,?avg(sal) FROM table1

? ? ??GROUP BY?deptno

? ? ? HAVING avg(sal)>?(SELECT avg(sal) FROM?table1);

??:分組語句中,SELECT后只能跟分組字段、函數(shù)及常數(shù),不能使用非分組函數(shù);

解析思路:

HAVING子句中限定組的篩選條件。題目中,需計算出各部門的平均工資,并篩選出符合條件的部門(部門就是分組標準)。

子查詢語句中,計算出部門整體的平均工資,然后將各部門的平均工資與之對比。

1.4在FROM子句中使用子查詢

FROM子句限定查詢的數(shù)據(jù)表,使用子查詢,即將子查詢的結果作為一張臨時的數(shù)據(jù)表使用。

題目:emp表:部門編號(deptno),姓名(name),工資(sal),職位(job),雇傭日期(hiredate)

篩選出公司每個員工的編號,姓名,工資,職位,雇傭日期,部門最大工資,部門最小工資

題目分析:

要求的取值結果中,包含分組統(tǒng)計的內容(部門最大最小值)及數(shù)據(jù)表其他字段。

分組情況下,SELECT子句僅可跟分組字段,函數(shù),常量。題目需要展示非分組字段。

因此,需要把分組統(tǒng)計的結果單獨查詢出作為一個數(shù)據(jù)表,將此表與原表進行聯(lián)結。

SELECT e.deptno,e.name,e.sal,e.job,e.hiredate,t.max,t.min

FROM emp e,

? ? ? ? ? ?(SELECT deptno,max(sal) max,min(sal) min FROM emp GROUP BY deptno) t

WHERE e.deptno=t.deptno;

2.關聯(lián)子查詢

關聯(lián)子查詢:子查詢不可獨立執(zhí)行,子查詢中使用主查詢的列作為條件。先執(zhí)行外部查詢,將外部查詢出的每條數(shù)據(jù)傳遞給子查詢語句執(zhí)行,子查詢執(zhí)行一次返回執(zhí)行結果后,主查詢根據(jù)子查詢結果進行決策。

2.1在細分的組內進行比較

題目1:根據(jù)各個部門的平均工資,查詢超過本部門平均工資的員工信息。

🙅錯誤寫法

🙅SELECT * FROM table1

? ? ? WHERE sal?>(SELECT avg(sal) FROM?table1 GROUP BY deptno);

錯誤原因:在子查詢中查每個部門的平均工資,但是是多行多列的結果。WHERE條件后,當子查詢結果為單行單列時,才能進行正常比較。

🙆正確寫法

🙆SELECT * FROM table1 t1

? ? ? WHERE sal?>(SELECT avg(sal) FROM?table1 t2 WHERE t1.deptno=t2.deptno);

上面子查詢的語句為關聯(lián)子查詢,子查詢的where子句中使用了主查詢的字段列作為限定條件。

在執(zhí)行這條語句時,取出主查詢中的一條員工數(shù)據(jù),傳入子查詢中,在子查詢中篩選此員工同部門的數(shù)據(jù),計算部門的平均工資。主查詢中將此員工工資和同部門的平均工資對比,符合條件則保留員工數(shù)據(jù)。然后再取下一個員工,重復執(zhí)行以上過程。

2.2使用EXISTS,NOT EXISTS時使用關聯(lián)子查詢

題目:用戶表customer 訂單表order?

求沒有下過訂單的客戶的信息

🙆SELECT * FROM customer c

? ? ? WHERE not exists?

?? ? ? ? ? ? ? ? ? ??(SELECT customer_id?FROM order o?WHERE c.customer_id=o.customer_id);

假設張三下了訂單,李四沒有下訂單。

那么在語句執(zhí)行的時候,通過外查詢語句取張三的信息,通過子查詢中的WHERE判斷,子查詢可取出一條數(shù)據(jù),不符合not exists,此條數(shù)據(jù)不保留。

取李四的數(shù)據(jù),通過子查詢中的where判斷,子查詢無符合條件的數(shù)據(jù),符合not exists,此條數(shù)據(jù)保留。

EXISTS,NOT EXISTS還有更復雜的用法,后續(xù)可以單獨介紹一下。看到一篇講的比較詳細的文章,大家如果有興趣可以移步至:

EXISTS,NOT EXISTS

總結

以上是生活随笔為你收集整理的SQL基础系列(五)——子查询的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內容還不錯,歡迎將生活随笔推薦給好友。