Oracle SQL - 根据月份对时间序列分区求和

时间:2016-11-21 19:04:25

标签: sql oracle automation window

我正在使用如下所示的数据集:

MTD       | ID | Active
-----------------------
01-APR-16 | A  | y
01-MAY-16 | A  | y
01-JUN-16 | A  | n
01-JUL-16 | A  | y
01-AUG-16 | A  | n
01-APR-16 | B  | n
01-MAY-16 | B  | y
01-JUN-16 | B  | y
01-JUL-16 | B  | y
01-AUG-16 | B  | y

我想在数据集中添加一个计数列,用于计算ID在当前MTD之后的活动次数(' y')。所需的输出是:

MTD       | ID | Active | COUNT
-------------------------------
01-APR-16 | A  | y      | 2
01-MAY-16 | A  | y      | 1
01-JUN-16 | A  | n      | 1
01-JUL-16 | A  | y      | 0
01-AUG-16 | A  | n      | 0
01-APR-16 | B  | n      | 4
01-MAY-16 | B  | y      | 3
01-JUN-16 | B  | y      | 2
01-JUL-16 | B  | y      | 1
01-AUG-16 | B  | y      | 0

我想到的问题是:

SELECT 
 MTD,

 ID, 

 ACTIVE,

 SUM(CASE WHEN MTD > (current records MTD) 
          AND ACTIVE = 'y' THEN 1 ELSE 0 END) 
          OVER (PARTITION BY ID) 
   as COUNT

我不确定如何将每个记录的MTD与窗口总和中当前记录的MTD进行比较。如何修改案例陈述的第一行?

谢谢,

Ryan Barker

2 个答案:

答案 0 :(得分:3)

count() over()range规范一起使用,以便查看活动标记y的当前行(对于每个id)后面的行,并仅计算它们。这假定mtd是一个date列,可以使订单生效。

SELECT 
 MTD,
 ID, 
 ACTIVE,
 COUNT(case when active='y' then 1 end) OVER(partition by ID order by mtd range between 1 following and unbounded following)
FROM your_table

<强> Python defaultdict and lambda

答案 1 :(得分:0)

对我来说,看起来你想要用&#34; y&#34;来计算行数。相反。像这样:

select t.*,
       greatest(sum(case when active = 'y' then 1 else 0 end) over (partition by id order by mtd desc) - 1,
                0)
from t;

你的想法非常接近。您只需要在分区子句中使用order by