当前位置: 首页 > news >正文

MySQL的窗口函数(Window Functions)

一、窗口函数核心概念

  1. ​窗口(Window)​
    窗口是数据行的集合,由OVER()子句定义。它决定了函数计算的“数据范围”,可以是一个分区的全部行、当前行前后的行,或动态变化的子集。

  2. ​语法结构​

    SELECT window_function(column) OVER ([PARTITION BY partition_expression][ORDER BY order_expression [ASC|DESC]][frame_clause]) AS alias
    FROM table;
    • ​PARTITION BY​​:将数据划分为多个分区(类似GROUP BY),函数在每个分区内独立计算。
    • ​ORDER BY​​:定义分区内数据的排序方式,影响窗口函数的计算顺序。
    • ​frame_clause​​:定义窗口的具体范围(如当前行及其前后N行)。

二、窗口函数分类及示例

1. 聚合类窗口函数

普通聚合函数(如SUMAVGCOUNT)结合OVER()使用,实现累计、移动平均等效果。

​示例:计算累计销售额​

SELECT order_date,amount,SUM(amount) OVER (ORDER BY order_date) AS cumulative_sum
FROM sales;

结果:

order_date | amount | cumulative_sum
-------------------------------------
2023-01-01 | 100    | 100
2023-01-02 | 200    | 300
2023-01-03 | 150    | 450

2. 排名类窗口函数
  • ROW_NUMBER()​:为每行分配唯一序号(相同值也会不同)。
  • RANK()​:相同值的行排名相同,后续序号跳跃(如1,1,3)。
  • DENSE_RANK()​:相同值的行排名相同,后续序号连续(如1,1,2)。

​示例:按销售额排名​

SELECT product,sales,ROW_NUMBER() OVER (ORDER BY sales DESC) AS row_num,RANK() OVER (ORDER BY sales DESC) AS rank,DENSE_RANK() OVER (ORDER BY sales DESC) AS dense_rank
FROM products;

结果:

product | sales | row_num | rank | dense_rank
--------------------------------------------
A       | 500   | 1       | 1    | 1
B       | 500   | 2       | 1    | 1
C       | 400   | 3       | 3    | 2

3. 分布类窗口函数
  • PERCENT_RANK()​:计算行的相对排名百分比(范围[0,1])。
  • CUME_DIST()​:计算行的累积分布(当前行及其之前行的占比)。

​示例:计算销售额分布​

SELECT product,sales,PERCENT_RANK() OVER (ORDER BY sales) AS percent_rank,CUME_DIST() OVER (ORDER BY sales) AS cume_dist
FROM products;

4. 前后函数
  • LAG(column, N)​:获取当前行​​前N行​​的值。
  • LEAD(column, N)​:获取当前行​​后N行​​的值。

​示例:计算销售额环比增长​

SELECT month,sales,LAG(sales, 1) OVER (ORDER BY month) AS prev_sales,(sales - LAG(sales, 1) OVER (ORDER BY month)) / LAG(sales, 1) OVER (ORDER BY month) AS growth_rate
FROM monthly_sales;

结果:

month | sales | prev_sales | growth_rate
----------------------------------------
Jan   | 1000  | NULL       | NULL
Feb   | 1200  | 1000       | 0.2
Mar   | 1500  | 1200       | 0.25

三、窗口帧(Frame Clause)

通过ROWSRANGE定义窗口的具体范围:

  • ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW​:从分区开始到当前行。
  • ROWS BETWEEN 1 PRECEDING AND 1 FOLLOWING​:当前行的前一行到后一行。

​示例:计算3个月移动平均​

SELECT month,sales,AVG(sales) OVER (ORDER BY monthROWS BETWEEN 2 PRECEDING AND CURRENT ROW) AS moving_avg
FROM monthly_sales;

结果:

month | sales | moving_avg
---------------------------
Jan   | 100   | 100.0
Feb   | 200   | 150.0
Mar   | 150   | 150.0
Apr   | 300   | 216.7

四、使用场景

  1. ​排名与分组排名​​:按部门、时间等分区后排序。
  2. ​累计计算​​:累计销售额、年累计增长率。
  3. ​移动统计​​:移动平均、移动求和。
  4. ​数据对比​​:当前行与前一行的差值或比率。

五、注意事项

  1. ​MySQL版本​​:窗口函数需MySQL 8.0+,旧版本不支持。
  2. ​性能优化​​:合理使用索引和分区,避免全表扫描。
  3. ​执行顺序​​:窗口函数在WHEREGROUP BYHAVING之后执行。

相关文章:

  • 【图像轮廓特征查找】图像处理(OpenCV) -part8
  • PyTorch 线性回归详解:模型定义、保存、加载与网络结构
  • 动态LOD策略细节层级控制:根据视角距离动态简化远距量子态渲染
  • Vue的模板编译过程
  • 【漏洞复现】CVE-2024-38856(ApacheOfbiz RCE)
  • 毕设 - 数字孪生智慧农场(vue+高德地图)项目分享
  • 记一次 .NET某旅行社酒店管理系统 卡死分析
  • SystemWeaver详解:从入门到精通的深度实战指南
  • 足球 AI 智能体技术解析:从数据采集到比赛预测的全链路架构
  • 【Maven基础】
  • 基于单片机的BMS热管理功能设计
  • 突破网页数据集获取难题:Web Unlocker API 助力 AI 训练与微调数据集全方位解决方案
  • Oracle EBS R12.2 安装 -- Step by Step
  • android studio sdk unavailable和Android 安装时报错:SDK emulator directory is missing
  • 计算机视觉——利用AI幻觉检测图像是否是生成式算生成的图像
  • 2025年最新服务器、中间件安全(面试题)
  • 系统架构设计(二):基于架构的软件设计方法ABSD
  • Java BIO、NIO、AIO、Netty面试题(已整理全套PDF版本)
  • 链表与文件
  • 日志的实现
  • 现货黄金价格站上3400美元,今年迄今累涨逾29%
  • 针对“二选一”,美团再次辟谣
  • 从沙漠到都市:贝亲世界地球日特别行动,以桃叶冰爽力开启地球降温之旅
  • 商务部:服务业扩大开放试点任务多数来源于经营主体实际需要
  • 中汽协发布规范驾驶辅助宣传与应用倡议书
  • 上海农房翻建为何难?基层盼政策适度松动