模块 7 · 第 2 课(共 4)课程中的26/57~14 min
模块课程(2/4)
窗口函数:排名和每组计算
窗口函数是对“行组”进行操作的函数
(window)但是 - 与 GROUP BY 不同 - 不会减少
rows:在窗口上计算的值附加到每一行
最终结果。
它是排名、渐进编号、百分比的正确工具
超过一个组总数,以及许多其他尴尬或
对于 GROUP BY 是不可能的。
语法:function() OVER (…)
SQL
ROW_NUMBER() OVER (PARTITION BY colonna ORDER BY colonna2)成分:
PARTITION BY— 定义“组”(如GROUP BY,但行 保持分开);ORDER BYinsideOVER(…)— 定义内的顺序 分区。
OVER ()(空括号)表示“整个表作为单个窗口”。
对于“总数的百分比”等计算很有用。
排名功能
SQL
ROW_NUMBER() OVER (PARTITION BY p ORDER BY o)
RANK() OVER (PARTITION BY p ORDER BY o)
DENSE_RANK() OVER (PARTITION BY p ORDER BY o)差异(值为 100, 100, 90, 80):
| 功能 | 职位 |
|---|---|
ROW_NUMBER | 1, 2, 3, 4(始终是唯一的) |
RANK | RANK 1, 1, 3, 4(关系共享一个位置,留下“间隙”) |
DENSE_RANK | 1, 1, 2, 3(关系共享一个位置,无间隙) |
示例:每个类别的产品排名
SQL
SELECT name,
category_id,
price,
RANK() OVER (PARTITION BY category_id ORDER BY price DESC) AS rank
FROM products
ORDER BY category_id, rank;对于每个 category_id , RANK 从 1 重新开始并按降序排列
价格:您可以在一个类别中每个类别内的产品排名
射击。
渐进编号
SQL
-- Progressive order number for each customer:
SELECT id,
customer_id,
ordered_at,
ROW_NUMBER() OVER (PARTITION BY customer_id ORDER BY ordered_at) AS row_num
FROM orders
ORDER BY customer_id, row_num;每个客户的第一个订单将具有 row_num = 1,第二个订单将具有 2,依此类推。
尝试一下
锻炼#sql.m7.l2.e1
尝试:0加载中...
对于每个产品,显示名称、category_id、价格和排名(按类别内价格降序排名;使用 RANK)。按类别_id 升序和排名升序排序。
正在加载编辑器...
显示提示
PARTITION BYcategory_id 组,ORDER BY 组内价格 DESC 订单。
3 次尝试后可用的解决方案
复习练习
锻炼#sql.m7.l2.e2
尝试:0加载中...
对于每个订单,显示 id、customer_id、ordered_at 和 row_num(每个客户的渐进 ROW_NUMBER,按 ordered_at 升序排序)。按 customer_id 和 row_num 排序。
正在加载编辑器...
显示提示
ROW_NUMBER 在分区内始终是唯一的。
3 次尝试后可用的解决方案