高級SQL分析函數-窗口函數

      2023-08-15 09:33:56 來源:博客園

      摘要:本文由葡萄城技術團隊于博客園原創并首發。轉載請注明出處:葡萄城官網,葡萄城為開發者提供專業的開發工具、解決方案和服務,賦能開發者。

      前言

      SQL語句中,聚合函數在統計業務數據結果時起到了重要作用,比如計算每個業務地區的業務總數、每個班級的學生平均分以及每個分類的最大值等。然而,今天我將介紹窗口函數,與聚合函數相比,它們也是一組函數,但在使用方法和適用場景上有所不同。在本章節中,我將重點介紹窗口函數中的RANK和DENSE_RANK函數,以及它們在排名和篩選方面的應用場景。這些窗口函數可以幫助我們更靈活地處理數據并獲得所需的結果,需要注意的是,目前主流的數據庫對窗口函數的最低需求版本如下:

      Mysql (>=8.0)PostgreSQL(>=8.4)SQL Server(>2005)SQLite(>3.25.0)


      (資料圖片)

      如果您的數據庫版本低于上述要求,將無法使用窗口函數。

      需求背景:

      為了讓大家更好的理解,我將以學生數據作為查詢的條件背景:假設現在某個學校的某個年級的同學完成了一次考試,成績也已經錄入到數據庫中:

      現在該年級的教務主任想要看一下:

      1.這次考試本年級各個科目的前2名的同學。

      2.這次考試每個班級中各個科目的前2名。

      3.這次考試每個班級中的總分排名前2名。

      如果用普通的SQL查詢即麻煩也費時間,而使用RANK和DENSE_RANK函數就可以很快的查詢出想要的學生數據,下面將為大家介紹如何使用RANK和DENSE_RANK函數實現學生數據的查詢。

      使用聚RANK和DENSE_RANK函數查詢學生數據1.查詢本年級各個科目前2名的同學。

      為了獲得各個不同科目各自的前2名,我們需要先使用 Rank() 函數來給每個學生在各自科目的分區打上成績排名, 執行如下SQL 語句,查詢出來的結果如下圖。

      select sd.*, RANK() over(partition by subject order by score desc) as _rank from score_data sd;

      可以看到,執行結果里面已經根據各個科目的成績得到了排名字段 _rank, 接下來只需要使用過濾掉 _rank 字段大于2的部分即可,查詢的結果如下圖所示。

      select * from (select sd.*, RANK() over(partition by subject order by score desc) as _rank from score_data sd) tmpwhere tmp._rank <=2

      從上圖中看到如果存在成績一樣的情況,就會出現像數學科目的查詢結果:數學查詢出來了三個值(因為有兩個人的數學成績是一樣的77分),如果我們只想保留一條重復的數據,我們可以使用DENSE_RANK函數,這個函數的計算語法和 RANK 基本一致,唯一不同的點在于, Rank 計算時會得到成績高于當前行的記錄的總行數,也就是上圖查詢出來的數學科目的三條數據,而DENSE_RANK 則是計算成績高于當前行的去重記錄的總行數,也就是說,如果出現像上圖的數學科目中的重復的數據,就會去掉重復的數據。

      2.查詢每個班級中各個科目的前2名。

      查詢每個班級中各個科目的前2名只需要在第一步(查詢本年級各個科目前2名的同學)的加上一個 class 班級的分區規則即可,查詢的結果如下圖所示:

      select * from (select sd.*, RANK() over(partition by subject, class order by score desc) as _rank from score_data sd) tmpwhere tmp._rank <=2
      3. 查詢每個班級中的總分排名前2名。

      同理,在第二步(查詢score_data表中每個班級中各個科目的前2名)的基礎上再添加一個成績的總和SUM(score)函數即可查詢每個班級中的總分前兩名。

      select class,name,SUM(score) AS total_score,RANK() over (PARTITION by class order by SUM(score) desc)from score_data sd group by class,name

      在這個指標的計算中,需要把聚合函數和排名函數結合起來使用,因為每個人的總成績被拆分為了多個科目的和,所以需要在班級和科目的聯合分組維度上進行聚合,把數據壓縮到每人總分的顆粒度。

      總結

      窗口函數是 SQL 函數中非常強大的工具,尤其是在報表統計等場景領域。它們不僅能夠簡化復雜的數據計算和分析,還能提高查詢效率和靈活性。窗口函數就像是數據庫操作中最鋒利的瑞士軍刀,為我們提供了一種強大而精確的方式來處理數據。

      擴展鏈接:

      Spring Boot框架下實現Excel服務端導入導出

      項目實戰:在線報價采購系統(React +SpreadJS+Echarts)

      Svelte 框架結合 SpreadJS 實現純前端類 Excel 在線報表設計

      關鍵詞:

      Copyright @  2015-2022 中南網版權所有 關于我們 備案號: 浙ICP備2022016517號-4   聯系郵箱:514 676 113@qq.com

      亚洲s色大片在线观看| 亚洲中文字幕无码一区| 亚洲天堂中文字幕| 亚洲AV无码欧洲AV无码网站| 亚洲中文字幕在线第六区| 怡红院亚洲怡红院首页| 中文字幕亚洲激情| 亚洲伊人成无码综合网| 亚洲一区无码精品色| 亚洲精品97久久中文字幕无码| 亚洲国产黄在线观看| 亚洲熟女乱综合一区二区| 久久影视综合亚洲| 亚洲精品亚洲人成在线观看| 九月丁香婷婷亚洲综合色| 久久精品国产亚洲香蕉| 日韩亚洲AV无码一区二区不卡| 4444亚洲国产成人精品| 亚洲国产午夜电影在线入口| 亚洲精品午夜国产va久久| 亚洲一区二区三区写真| 国产精品亚洲专区无码牛牛| 亚洲第一成人影院| 亚洲一区AV无码少妇电影☆| 亚洲国产精品成人精品无码区 | 亚洲av无码有乱码在线观看| 色噜噜噜噜亚洲第一| 亚洲精品和日本精品| 亚洲日本va中文字幕久久| 亚洲av永久无码精品秋霞电影影院| 亚洲AV人无码综合在线观看| 亚洲精品国产成人中文| 国产成人精品日本亚洲11| 亚洲成av人无码亚洲成av人| 亚洲第一页日韩专区| 亚洲精品夜夜夜妓女网| 中文字幕亚洲综合久久| 一本天堂ⅴ无码亚洲道久久| 婷婷亚洲综合五月天小说在线| 久久精品国产亚洲一区二区三区| 国产成A人亚洲精V品无码 |