当前位置: 首页 > 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之后执行。
http://www.xdnf.cn/news/65989.html

相关文章:

  • 实训Day-1 漏洞攻击实战
  • 【LeetCode 热题 100】哈希、双指针、滑动窗口
  • 【Markdown】【HTML】在Markdown中实现康奈尔笔记模式(右侧留白)
  • 算法分析与设计——动态规划复习题(待更新
  • Flutter 状态管理 Riverpod
  • 华为IPD流程变革如何推动组织转型?2025变革路径
  • 从代码实现理解Vision Permutator:WeightedPermuteMLP模型解析
  • Java并发编程-线程池
  • spark–sql项目实验
  • 声学重构+交互创新,特伦斯便携钢琴V30Pro专业演奏的移动化时代
  • 信息收集之hack用的网络空间搜索引擎
  • 文件有几十个T,需要做rag,用ragFlow能否快速落地呢?
  • PCB原理图解析(炸鸡派为例)
  • Google独立站和阿里国际站不是一回事
  • Python爬虫与代理IP:高效抓取数据的实战指南
  • Web开发:ABP框架10——使用数据库存储文件,完成文件的下载和上传
  • 【第四章】19-匹配规则定义
  • GPT-4.1 开启智能时代新纪元
  • 算法之动态规划
  • 第42讲:走进智慧农业的“感知神经系统”——农田遥感 + 边缘计算的融合实践
  • WiFi模块使用AT+lwip上网
  • 苹果开发者账号 3.2(f) 被封排查思路及重生指南
  • 在 Spring Boot 项目中怎么识别和优化慢 SQL ?
  • 每日一题——数据中心网络地址规划
  • 简易版自制RTOS
  • AI律师匹配AI分析法律需求意图并匹配律师
  • 7. 服务通信 ---- 使用自定义srv,服务方和客户方cpp,python文件编写
  • 操作指南:在vue-fastapi-admin上增加新的功能模块
  • 江湖密码术:Rust中的 bcrypt 加密秘籍
  • 算法 | 成长优化算法(Growth Optimizer,GO)原理,公式,应用,算法改进研究综述,matlab代码