over(order by xxx) 按照xxx字段排序进行累计,order by是一个默认的开窗函数;
over (partition by xxx,yyy)按照 xxx,yyy 字段分区;
over (partition by xxx order by yyy)按照 xxx 字段分区,并按照yyy字段排序进行累计。
声明:以下数据均为测试数据。
测试表 test_2021 的表结构如下:
名称 | 类型 | 可为空 | 注释 |
---|---|---|---|
YEAR_NAME | VARCHAR2(19) | Y | 年份名称 |
MONTH_NAME | VARCHAR2(11) | Y | 月份名称 |
POST_CODE | VARCHAR2(52) | Y | 岗位编码 |
POST_NAME | VARCHAR2(300) | Y | 岗位名称 |
TESTTYPE_CODE | CHAR(2) | Y | 试验类型编码 |
TESTTYPE_NAME | CHAR(6) | Y | 试验类型名称 |
COST_AMT | NUMBER | Y | 产值 |
测试表 test_2021的部分数据如下:
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 |
---|---|---|---|---|---|---|
2017年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 460 |
2018年 | 02月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 356 |
2018年 | 04月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 980 |
2019年 | 12月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 366 |
2019年 | 05月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 716 |
2020年 | 07月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 681 |
2017年 | 12月 | 7 | 电连接器器件检测岗 | 1 | 筛选 | 325 |
2019年 | 02月 | 8 | 机电元件检测岗 | 2 | 复验 | 274 |
2018年 | 06月 | 8 | 机电元件检测岗 | 1 | 筛选 | 876 |
2019年 | 07月 | 8 | 机电元件检测岗 | 2 | 复验 | 349 |
2019年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 292 |
2019年 | 08月 | 8 | 机电元件检测岗 | 1 | 筛选 | 837 |
2020年 | 02月 | 8 | 机电元件检测岗 | 2 | 复验 | 250 |
2020年 | 03月 | 8 | 机电元件检测岗 | 1 | 筛选 | 470 |
2020年 | 09月 | 8 | 机电元件检测岗 | 1 | 筛选 | 453 |
2019年 | 05月 | 8 | 机电元件检测岗 | 1 | 筛选 | 348 |
2018年 | 01月 | 8 | 机电元件检测岗 | 1 | 筛选 | 707 |
2020年 | 02月 | 8 | 机电元件检测岗 | 1 | 筛选 | 244 |
2018年 | 10月 | 8 | 机电元件检测岗 | 1 | 筛选 | 45 |
需求:按照岗位编码,岗位名称,试验类型编码,试验类型名称以及年份进行分区求产值的累计和,求出了同一年份同一岗位同一试验类型的不同月份的产值的和。
select
year_name,--年份名称
month_name,--月份名称
post_code,--岗位编码
post_name,--岗位名称
testtype_code,--试验类型编码
testtype_name,--试验类型名称
cost_amt,--产值
sum(cost_amt) over (partition by post_code,post_name,testtype_code,testtype_name,year_name) as leiji_amt--累计产值
from test_2021
where year_name = '2016年'
order by year_name,month_name
执行结果如下:
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|
2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 1261 |
2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 824 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 1098 |
2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 464 |
2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 871 |
2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 1362 |
2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 1021 |
2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 1457 |
2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 1723 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 1098 |
2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 464 |
2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 1362 |
2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 1457 |
2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 824 |
2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 1021 |
2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 871 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 1261 |
2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 1723 |
我们将以上数据按累计产值排序以后,会更直观的看出同一年份同一岗位同一试验类型的不同月份的产值的和。
比如累计产值为464的值,就是2016年 电连接器器件检测岗 复验 这种试验11月份和12月份的和。
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|
2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 464 |
2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 464 |
2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 824 |
2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 824 |
2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 871 |
2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 871 |
2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 1021 |
2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 1021 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 1098 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 1098 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 1261 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 1261 |
2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 1362 |
2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 1362 |
2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 1457 |
2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 1457 |
2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 1723 |
2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 1723 |
那么我们猜想,如果按照年份,以及试验类型分区求和的话,那么出来的累计产值是不是只有两个值,一个是2016年复验试验的产值,一个是2016年筛选试验的产值,测试SQL如下:
select
year_name,--年份名称
month_name,--月份名称
post_code,--岗位编码
post_name,--岗位名称
testtype_code,--试验类型编码
testtype_name,--试验类型名称
cost_amt,--产值
sum(cost_amt) over (partition by year_name,testtype_code,testtype_name) as leiji_amt--累计产值
from test_2021
where year_name = '2016年'
order by year_name,month_name
该SQL执行结果如下(按累计产值排序):
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|
2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 4782 |
2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 4782 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 4782 |
2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 4782 |
2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 4782 |
2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 4782 |
2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 4782 |
2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 4782 |
2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 4782 |
2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 4782 |
2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 5299 |
2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 5299 |
2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 5299 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 5299 |
2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 5299 |
2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 5299 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 5299 |
2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 5299 |
需求:按照年月进行累计,即2016年11月的累计产值为11的和(2016年只有11月以后的数据),12月为11月和12月的和,SQL如下
select
year_name,--年份名称
month_name,--月份名称
post_code,--岗位编码
post_name,--岗位名称
testtype_code,--试验类型编码
testtype_name,--试验类型名称
cost_amt,--产值
sum(cost_amt) over (order by year_name,month_name) as leiji_amt--累计产值
from test_2021
where year_name = '2016年'
order by year_name,month_name
执行结果如下:
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|
2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 5705 |
2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 5705 |
2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 5705 |
2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 5705 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 5705 |
2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 5705 |
2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 5705 |
2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 5705 |
2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 5705 |
2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 10081 |
2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 10081 |
2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 10081 |
2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 10081 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 10081 |
2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 10081 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 10081 |
2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 10081 |
2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 10081 |
作为对比,同样的SQL,我们将 order by 改为 partition by ,看一下结果,SQL以及执行结果如下:
select
year_name,--年份名称
month_name,--月份名称
post_code,--岗位编码
post_name,--岗位名称
testtype_code,--试验类型编码
testtype_name,--试验类型名称
cost_amt,--产值
sum(cost_amt) over (partition by year_name,month_name) as leiji_amt--累计产值
from test_2021
where year_name = '2016年'
order by year_name,month_name
年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|
2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 5705 |
2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 5705 |
2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 5705 |
2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 5705 |
2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 5705 |
2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 5705 |
2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 5705 |
2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 5705 |
2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 5705 |
2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 4376 |
2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 4376 |
2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 4376 |
2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 4376 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 4376 |
2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 4376 |
2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 4376 |
2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 4376 |
2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 4376 |
以上11月产值5705加上12月的产值4376等于10081,刚好为 order by 中的12月累计值10081。
需求:求出同一年份,同一岗位,同一试验类型每个月的产值累计值。这里既要按年份、岗位、试验类型分区,又要求月份的累计值,所以就要用over (partition by xxx order by yyy),SQL如下:
select
year_name,--年份名称
month_name,--月份名称
post_code,--岗位编码
post_name,--岗位名称
testtype_code,--试验类型编码
testtype_name,--试验类型名称
cost_amt,--产值
sum(cost_amt) over (partition by year_name,post_code,post_name,testtype_code,testtype_name order by month_name) as leiji_amt
from test_2021
where year_name = '2016年'
order by year_name,month_name
执行结果如下:
序号 | 年份名称 | 月份名称 | 岗位编码 | 岗位名称 | 试验类型编码 | 试验类型名称 | 产值 | 累计产值 |
---|---|---|---|---|---|---|---|---|
1 | 2016年 | 11月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 884 | 884 |
2 | 2016年 | 11月 | 6 | 微波器件检测岗 | 1 | 筛选 | 388 | 388 |
3 | 2016年 | 11月 | 8 | 机电元件检测岗 | 2 | 复验 | 874 | 874 |
4 | 2016年 | 11月 | 8 | 机电元件检测岗 | 1 | 筛选 | 640 | 640 |
5 | 2016年 | 11月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 57 | 57 |
6 | 2016年 | 11月 | 6 | 微波器件检测岗 | 2 | 复验 | 802 | 802 |
7 | 2016年 | 11月 | 5 | 分立器件检测岗 | 2 | 复验 | 795 | 795 |
8 | 2016年 | 11月 | 5 | 分立器件检测岗 | 1 | 筛选 | 874 | 874 |
9 | 2016年 | 11月 | 4 | 阻容元件检测岗 | 2 | 复验 | 391 | 391 |
10 | 2016年 | 12月 | 6 | 微波器件检测岗 | 1 | 筛选 | 633 | 1021 |
11 | 2016年 | 12月 | 8 | 机电元件检测岗 | 2 | 复验 | 488 | 1362 |
12 | 2016年 | 12月 | 5 | 分立器件检测岗 | 2 | 复验 | 76 | 871 |
13 | 2016年 | 12月 | 8 | 机电元件检测岗 | 1 | 筛选 | 817 | 1457 |
14 | 2016年 | 12月 | 4 | 阻容元件检测岗 | 1 | 筛选 | 214 | 1098 |
15 | 2016年 | 12月 | 6 | 微波器件检测岗 | 2 | 复验 | 22 | 824 |
16 | 2016年 | 12月 | 4 | 阻容元件检测岗 | 2 | 复验 | 870 | 1261 |
17 | 2016年 | 12月 | 7 | 电连接器器件检测岗 | 2 | 复验 | 407 | 464 |
18 | 2016年 | 12月 | 5 | 分立器件检测岗 | 1 | 筛选 | 849 | 1723 |
数据核对:以2016年阻容元件检测岗的筛选试验为例,在11月的产值为884(第1行数据),累计产值为884,在12月的产值为214(第14行数据),12月的累计产值为1098,即为11月的884与12月的214的和。