SQL實戰:03之SQL中的遞歸查詢

文章目錄

  • 概述
  • SQL 中的遞歸實現
  • 題目一:分析組織層級
  • 題解
  • 題目二:樹節點求解
  • 題解
    • 步驟一:通過遞歸查詢出每個節點的上級節點和下級節點分布
    • 步驟二:分組統計

概述

最近刷題時遇到了一道需要根據組織層級來統計各個層級的一些數據,當時碰到時的第一想法就是需要使用遞歸來實現。但是以前在SQl中從來就沒有用過遞歸查詢,后面到網上一搜索,居然還真有遞歸查詢的實現,也算是給自己掃了一下盲了。

SQL 中的遞歸實現

遞歸是一種通過自身調用自身來 逐步推理出計算結果的一種思想。在SQL中遞歸查詢同樣也是如此,通過自身調用自身來逐步構建查詢結果。一般多用于處理具有層次結構的數據,如樹形結構、組織結構圖、文件系統目錄等。
在SQL中,使用 WITH RECURSIVE 關鍵字來實現。

同編程語言中的遞歸函數調用類似,遞歸查詢的執行過程也需要遵循以下三個原則:

  • 初始查詢
    首次執行初始查詢 ,得到一個初始結果集。
  • 遞歸調用
    將初始結果集作為輸入,執行遞歸查詢,并將遞歸查詢的結果與初始結果集合并,作為下一次查詢的輸入。
  • 終止條件
    重復執行遞歸查詢,直到沒有新的行可以添加到結果集中,遞歸查詢終止。
    遞歸查詢的語法如下:
    WITH RECURSIVE table_name AS (--初始查詢SELECT 1 AS level FROM XXX WHERE XXXUNION ALL--遞歸查詢SELECT level+1  FROM table_name WHERE XXXX--終止條件是查詢到所有的記錄都做了處理,遞歸終止 )

例如使用遞歸生成一個連續的序列:

-- 遞歸查詢生成數字序列
WITH RECURSIVE lianxu_numbers AS (-- 初始查詢,生成第一個數字 1SELECT 1 AS numUNION ALL-- 遞歸查詢(遞歸成員):生成下一個數字SELECT num + 1FROM lianxu_numbersWHERE num < 100 -- 小于100 是終止條件
)
SELECT * FROM numbers;

題目一:分析組織層級

表:Employees+----------------+---------+
| Column Name    | Type    | 
+----------------+---------+
| employee_id    | int     |
| employee_name  | varchar |
| manager_id     | int     |
| salary         | int     |
| department     | varchar |
+----------------+----------+
employee_id 是這張表的唯一主鍵。
每一行包含關于一名員工的信息,包括他們的 ID,姓名,他們經理的 ID,薪水和部門。
頂級經理(CEO)的 manager_id 是空的。
編寫一個解決方案來分析組織層級并回答下列問題:層級:對于每名員工,確定他們在組織中的層級(CEO 層級為 1,CEO 的直接下屬員工層級為 2,以此類推)。
團隊大小:對于每個是經理的員工,計算他們手下的(直接或間接下屬)總員工數。
薪資預算:對于每個經理,計算他們控制的總薪資預算(所有手下員工的工資總和,包括間接下屬,加上自己的工資)。
返回結果表以 層級 升序 排序,然后以預算 降序 排序,最后以 employee_name 升序 排序。結果格式如下所示。示例:輸入:Employees 表:+-------------+---------------+------------+--------+-------------+
| employee_id | employee_name | manager_id | salary | department  |
+-------------+---------------+------------+--------+-------------+
| 1           | Alice         | null       | 12000  | Executive   |
| 2           | Bob           | 1          | 10000  | Sales       |
| 3           | Charlie       | 1          | 10000  | Engineering |
| 4           | David         | 2          | 7500   | Sales       |
| 5           | Eva           | 2          | 7500   | Sales       |
| 6           | Frank         | 3          | 9000   | Engineering |
| 7           | Grace         | 3          | 8500   | Engineering |
| 8           | Hank          | 4          | 6000   | Sales       |
| 9           | Ivy           | 6          | 7000   | Engineering |
| 10          | Judy          | 6          | 7000   | Engineering |
+-------------+---------------+------------+--------+-------------+
輸出:+-------------+---------------+-------+-----------+--------+
| employee_id | employee_name | level | team_size | budget |
+-------------+---------------+-------+-----------+--------+
| 1           | Alice         | 1     | 9         | 84500  |
| 3           | Charlie       | 2     | 4         | 41500  |
| 2           | Bob           | 2     | 3         | 31000  |
| 6           | Frank         | 3     | 2         | 23000  |
| 4           | David         | 3     | 1         | 13500  |
| 7           | Grace         | 3     | 0         | 8500   |
| 5           | Eva           | 3     | 0         | 7500   |
| 9           | Ivy           | 4     | 0         | 7000   |
| 10          | Judy          | 4     | 0         | 7000   |
| 8           | Hank          | 4     | 0         | 6000   |
+-------------+---------------+-------+-----------+--------+
解釋:組織結構:
Alice(ID:1)是 CEO(層級 1)沒有經理。
Bob(ID:2)和 Charlie(ID:3)是 Alice 的直接下屬(層級 2)
David(ID:4),Eva(ID:5)從屬于 Bob,而 Frank(ID:6)和 Grace(ID:7)從屬于 Charlie(層級 3)
Hank(ID:8)從屬于 David,而 Ivy(ID:9)和 Judy(ID:10)從屬于 Frank(層級 4)
層級計算:
CEO(Alice)層級為 1
每個后續的管理層級都會使層級數加 1
團隊大小計算:
Alice 手下有 9 個員工(除她以外的整個公司)
Bob 手下有 3 個員工(David,Eva 和 Hank)
Charlie 手下有 4 個員工(Frank,Grace,Ivy 和 Judy)
David 手下有 1 個員工(Hank)
Frank 手下有 2 個員工(Ivy 和 Judy)
Eva,Grace,Hank,Ivy 和 Judy 沒有直接下屬(team_size = 0)
預算計算:
Alice 的預算:她的工資(12000)+ 所有員工的工資(72500)= 84500
Charlie 的預算:他的工資(10000)+ Frank 的預算(23000)+ Grace 的工資(8500)= 41500
Bob 的預算:他的工資 (10000) + David 的預算(13500)+ Eva 的工資(7500)= 31000
Frank 的預算:他的工資 (9000) + Ivy 的工資(7000)+ Judy 的工資(7000)= 23000
David 的預算:他的工資 (7500) + Hank 的工資(6000)= 13500
沒有直接下屬的員工的預算等于他們自己的工資。
注意:結果先以層級升序排序
在同一層級內,員工按預算降序排序,然后按姓名升序排序

題解

with recursive a1 as (select employee_id,manager_id,1 as afrom employeesunion allselect a1.employee_id,e.manager_id,a+1from employees e  join a1 on a1.manager_id=e.employee_id
)
,
--level:層級
a2 as (select employee_id, count(*) levelfrom a1group by employee_id)/*level*/
,
--下屬人數
a3 as (select manager_id, count(*) team_sizefrom a1where manager_id is not nullgroup by manager_id)/*size*/
,
--工資統計
a4 as (select a1.manager_id, sum(salary) budgetfrom a1left join employees e using (employee_id)where a1.manager_id is not nullgroup by a1.manager_id
)select employee_id,employee_name,level,ifnull(team_size,0) team_size,salary+ifnull(budget,0) budget
from a2 left join employees using(employee_id)
left join a3 on a2.employee_id=a3.manager_id
left join a4 on a2.employee_id=a4.manager_id
order by level,budget desc,employee_name;

題目二:樹節點求解

表:Tree+-------------+------+
| Column Name | Type |
+-------------+------+
| id          | int  |
| p_id        | int  |
+-------------+------+
id 是該表中具有唯一值的列。
該表的每行包含樹中節點的 id 及其父節點的 id 信息。
給定的結構總是一個有效的樹。樹中的每個節點可以是以下三種類型之一:"Leaf":節點是葉子節點。
"Root":節點是樹的根節點。
"lnner":節點既不是葉子節點也不是根節點。
編寫一個解決方案來報告樹中每個節點的類型。以 任意順序 返回結果表。結果格式如下所示。示例 1:輸入:
Tree table:
+----+------+
| id | p_id |
+----+------+
| 1  | null |
| 2  | 1    |
| 3  | 1    |
| 4  | 2    |
| 5  | 2    |
+----+------+
輸出:
+----+-------+
| id | type  |
+----+-------+
| 1  | Root  |
| 2  | Inner |
| 3  | Leaf  |
| 4  | Leaf  |
| 5  | Leaf  |
+----+-------+
解釋:
節點 1 是根節點,因為它的父節點為空,并且它有子節點 2 和 3。
節點 2 是一個內部節點,因為它有父節點 1 和子節點 4 和 5。
節點 3、4 和 5 是葉子節點,因為它們有父節點而沒有子節點。

題解

步驟一:通過遞歸查詢出每個節點的上級節點和下級節點分布

with recursive a1 AS (select id,p_id, 1 as level from Treeunion allselect a1.id,e.p_id, level+1 as level from Tree e join a1 on a1.p_id = e.id
)
select * from a1;

輸出:

| id | p_id | level |
| -- | ---- | ----- |
| 1  | null | 1     |
| 2  | 1    | 1     |
| 3  | 1    | 1     |
| 4  | 2    | 1     |
| 5  | 2    | 1     |
| 3  | null | 2     |
| 2  | null | 2     |
| 5  | 1    | 2     |
| 4  | 1    | 2     |
| 4  | null | 3     |
| 5  | null | 3     |

得到上面這張零時表后,就可以根據這張臨時表統計出每個節點的下級節點的數量,每個節點所在的層次。

步驟二:分組統計

  • 統計節點所在層級
select id, count(*) as level from a1 group by id;
  • 統計幾點的下級節點(包括間接節點)的數量
select p_id, count(*) as son_nums from a1 where p_id is not null group by p_id;

子節點數為0的節點就為葉子節點。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/78944.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/78944.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/78944.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

MySQL 語法與基礎完全指南

MySQL 是最流行的開源關系型數據庫管理系統之一&#xff0c;廣泛應用于 Web 應用程序開發。本文將全面介紹 MySQL 的基礎知識和完整語法結構。 一、MySQL 基礎概念 1. 數據庫基本術語 數據庫(Database): 存儲數據的集合 表(Table): 數據以表格形式組織 列(Column): 表中的一…

【Sqlalchemy Model轉換成Pydantic Model示例】

【Sqlalchemy Model轉換成Pydantic Model示例】 由于Sqlalchemy和Pydantic的模型字段類型可能有差異, 所以需要一個通用的裝換類 def sqlalchemy_to_pydantic_v2(sqlalchemy_model, pydantic_model):"""通用函數&#xff0c;將 SQLAlchemy 模型實例轉換為 Pyd…

2025年歐洲西南部大停電

2025年4月28日&#xff0c;歐洲西南部出現大規模停電&#xff0c;西班牙、葡萄牙和法國南部均受到影響。有報道指出停電可能與 歐洲電網出現問題有關&#xff0c;但最終原因尚未確定。由于停電&#xff0c;上述地區的交通和通信服務均受到嚴重影響&#xff0c;交通信號燈停止工…

Java EE初階——計算機是如何工作的

1. cpu 馮諾依曼體系&#xff08;Von Neumann Architecture&#xff09; ? CPU 中央處理器: 進?算術運算和邏輯判斷. ? 存儲器: 分為外存和內存, ?于存儲數據(使??進制?式存儲) ? 輸?設備: ??給計算機發號施令的設備. ? 輸出設備: 計算機個??匯報結果的設…

飛鳥游戲模擬器 1.0.3 | 完全免費無廣告,內置大量經典童年游戲,重溫美好回憶

飛鳥游戲模擬器是一款專為安卓用戶設計的免費游戲模擬器&#xff0c;內置了大量經典的童年游戲。該模擬器擁有豐富的游戲資源&#xff0c;目前已有約20,000款游戲&#xff0c;包括多種類型如冒險、動作、角色扮演等。用戶可以直接搜索查找想要玩的游戲進行下載并啟動。游戲庫中…

網絡爬取需謹慎:警惕迷宮陷阱

一、技術背景:網絡爬蟲與數據保護的博弈升級 1. 問題根源:AI訓練數據爬取的無序性 數據需求爆炸:GPT-4、Gemini等大模型依賴數萬億網頁數據訓練,但大量爬蟲無視網站的robots.txt協議(非法律強制),未經許可抓取內容(如新聞、學術論文、代碼),引發版權爭議(如OpenAI被…

Qwen3簡介:大型語言模型的革命

Qwen3簡介&#xff1a;大型語言模型的革命 Qwen系列語言模型的最新發布——Qwen3&#xff0c;標志著人工智能&#xff08;AI&#xff09;技術的一次重大飛躍。基于前代版本的成功&#xff0c;Qwen3在架構、推理能力和多項先進功能上都取得了顯著提升&#xff0c;正在重新定義大…

MODSIM選型指南:汽車與航空航天企業如何選擇仿真平臺

1. 引言 在競爭激烈的汽車與航空航天領域&#xff0c;仿真技術已成為產品研發不可或缺的環節。通過在設計階段驗證概念并優化性能&#xff0c;仿真平臺能有效縮短開發周期并降低物理樣機制作成本。 MODSIM&#xff08;建模與仿真&#xff09;作為達索系統3DEXPERIENCE平臺的核…

linux 內核 debugfs 使用介紹

一&#xff1a;概述 debugfs 是 Linux 內核提供的一個特殊的虛擬文件系統&#xff0c;用于 暴露內核模塊&#xff08;如驅動&#xff09;內部的調試信息或控制接口&#xff0c;供開發者、調試人員實時查看和排查問題。即 debugfs 就是一個“調試專用的 /proc 或 /sys”&#xf…

ZYNQ筆記(十五):PL讀寫PS DDR(自定義IP核-AXI4接口)

版本&#xff1a;Vivado2020.2&#xff08;Vitis&#xff09; 任務&#xff1a;PL 端自定義一個 AXI4 接口的 IP 核&#xff0c;通過 AXI_HP 接口對 PS 端 DDR3 進行讀寫 測試&#xff0c;讀寫的內存大小是 4K 字節&#xff0c; 目錄 一、介紹 &#xff08;1&#xff09;…

Redis 小記

Redis 命令小記 Redis 是一個文本/二進制數據庫&#xff08;textual/binary database&#xff09; CLI 命令 redis-cli, redis-server, redis-benchmark, redis-check-dump, redis-check-aof redis-cli 執行命令 # 方式 1 redis-cli -h 127.0.0.1 -p 6379 > 127.0.0.1:63…

如何在idea中編寫spark程序

在 IntelliJ IDEA 中編寫 Spark 程序的詳細指南 在大數據處理領域&#xff0c;Apache Spark 憑借其強大的分布式計算能力&#xff0c;成為了眾多開發者的首選工具。而 IntelliJ IDEA 作為一款功能強大的集成開發環境&#xff08;IDE&#xff09;&#xff0c;為編寫 Spark 程序…

各類神經網絡學習:(十一)注意力機制(第3/4集),位置編碼

上一篇下一篇注意力機制&#xff08;2/4集&#xff09;注意力機制&#xff08;4/4集&#xff09; 位置編碼 R N N RNN RNN 和 L S T M LSTM LSTM 這些網絡都是串行執行的&#xff0c;在潛移默化中&#xff0c;就包含了順序關系&#xff0c;也就是詞序關系。而注意力機制是并行…

《Python Web部署應知應會》Flask網站隱藏或改變瀏覽器URL:從Nginx反向代理到URL重寫技術

Flask網站隱藏或改變瀏覽器顯示URL地址的實現方案&#xff1a;從Nginx反向代理到URL重寫技術 引言 在Web應用開發中&#xff0c;URL路徑的安全性往往被忽視&#xff0c;這可能導致網站結構和后端邏輯被攻擊者輕易推斷。對于Flask框架開發的網站&#xff0c;如何隱藏或改變瀏覽…

elementui里的el-tabs的內置樣式修改失效?

1.問題圖 紅框里的是組件的內置樣式&#xff0c;紅框下的是自定義樣式 2.分析 2.1scoped vue模板編譯器在編譯有scoped的stye標簽時&#xff0c;會生成對應的postCSS插件&#xff0c;該插件會給每個scoped標記的style標簽模塊&#xff0c;生成唯一一個對應的 data-v-xxxhash…

大數據測試集群環境部署

Hadoop大數據集群搭建&#xff08;超詳細&#xff09;_hadoop_小飛飛519-GitCode 開源社區 hadoop集群一之虛擬機安裝(mac)_hadoop_皮皮蝦不皮呀-華為開發者空間 hadoop集群二之hadoop安裝_hadoop_皮皮蝦不皮呀-華為開發者空間 虛擬機如何查看gateway | PingCode智庫

Nginx 核心功能筆記

目錄 一、Nginx 簡介 二、核心功能詳解 三、關鍵指令解析 四、性能優化要點 五、常見應用場景 一、Nginx 簡介 定位 高性能的 HTTP/反向代理服務器&#xff0c;同時支持郵件協議代理&#xff08;IMAP/POP3/SMTP&#xff09;。采用 事件驅動、異步非阻塞 架構&#xff0c;…

強化學習(二)馬爾科夫決策過程(MDP)

1. 簡介 馬爾可夫決策過程正式地描述了強化學習的環境其中環境是完全可觀測的即當前狀態完全表征了這個過程幾乎所有的強化學習問題都可以形式化為馬爾可夫決策過程&#xff0c;例如&#xff1a; 最優控制主要處理連續的馬爾可夫決策過程部分可觀察的問題可以轉化為馬爾可夫決…

Day16(貪心算法)——LeetCode45.跳躍游戲II763.劃分字母區間

1 LeetCode45.跳躍游戲II 1.1 題目描述 與跳躍游戲類似&#xff0c;跳躍游戲II給定長為n的從0開始索引的整數數組nums&#xff0c;nums[i]是你在i處能向右跳躍的最大步數&#xff0c;求到達數組最后一個索引處需要跳躍的最少次數。 ??一個示例&#xff1a;nums[2,3,1,1,4]&a…

告別碎片化!兩大先進分塊技術如何提升RAG的語義連貫性?

研究動機 論文核心問題及研究背景分析 1. 研究領域及其重要性 研究領域&#xff1a;檢索增強生成&#xff08;Retrieval-Augmented Generation, RAG&#xff09;系統&#xff0c;結合自然語言處理&#xff08;NLP&#xff09;與信息檢索技術。重要性&#xff1a; RAG通過動態…