将列值除以日期范围内的行数

时间:2017-08-15 00:04:36

标签: sql postgresql

我在Impala中有一个表格,其中包含字段:广告系列ID,帐户,开始日期,结束日期,交易日期和收入。有多个广告系列具有相同的帐户和收入值。我想在[Transaction_Date,Transaction_Date + 36个月]范围内的广告系列之间划分收入值 样本表:

    Campaign  | Account | Start Date | End Date | Trans. Date | Revenue
       1      |   1234  | 13-05-17   | 13-06-17 | 19-10-17    | 200
       2      |   1234  | 14-01-16   | 14-02-16 | 19-10-17    | 200
       2      |   5678  | 14-01-16   | 14-02-16 | 07-02-16    | 200
       3      |   2345  | 20-05-15   | 20-07-15 | 22-05-15    | 300
       4      |   1234  | 15-10-13   | 15-11-13 | 19-10-17    | 200
       4      |   5678  | 15-10-13   | 15-11-13 | 22-05-15    | 300

此处,帐户1234的收入应在广告系列1和2之间分配,而不是4,因为交易日期在广告系列开始后36个月。虽然帐户2345的收入应在活动2和4之间分配 所以结果表应该是:

    Campaign  | Account | Start Date | End Date | Trans. Date | Revenue | Avg Revenue
       1      |   1234  | 13-05-17   | 13-06-17 | 19-10-17    | 200     | 100
       2      |   1234  | 14-01-16   | 14-02-16 | 19-10-17    | 200     | 100
       2      |   5678  | 14-01-16   | 14-02-16 | 07-02-16    | 200     | 200
       3      |   2345  | 20-05-15   | 20-07-15 | 22-05-15    | 300     | 150
       4      |   1234  | 15-10-13   | 15-11-13 | 19-10-17    | 200     | NULL
       4      |   2345  | 15-10-13   | 15-11-13 | 22-05-15    | 300     | 150

编辑:
基本上,我想做以下事项:
1.对于每一行,获取该帐户的所有行,其中trans_date介于开始日期和开始日期之间+ 3年。
2.将每行中的收入除以行数 我试图使用分区来完成这项工作,但我不知道如何根据日期值创建一个具有可变范围的分区。
希望这更清楚 谢谢!

1 个答案:

答案 0 :(得分:0)

这将在Oracle中运行,该概念应该能够适应Postgres ..

drop table test;

create table test as
select 1 as Campaign, 1234 as Account, to_date('13-05-17', 'DD-MM-YY') as Start_Date, to_date('13-06-17', 'DD-MM-YY') as End_Date, to_date('19-10-17', 'DD-MM-YY') as Trans_Date, 200 as Revenue from dual union all
select 2 as Campaign, 1234 as Account, to_date('14-01-16', 'DD-MM-YY') as Start_Date, to_date('14-02-16', 'DD-MM-YY') as End_Date, to_date('19-10-17', 'DD-MM-YY') as Trans_Date, 200 as Revenue from dual union all
select 2 as Campaign, 5678 as Account, to_date('14-01-16', 'DD-MM-YY') as Start_Date, to_date('14-02-16', 'DD-MM-YY') as End_Date, to_date('07-02-16', 'DD-MM-YY') as Trans_Date, 200 as Revenue from dual union all
select 3 as Campaign, 2345 as Account, to_date('20-05-15', 'DD-MM-YY') as Start_Date, to_date('20-07-15', 'DD-MM-YY') as End_Date, to_date('22-05-15', 'DD-MM-YY') as Trans_Date, 300 as Revenue from dual union all
select 4 as Campaign, 1234 as Account, to_date('15-10-13', 'DD-MM-YY') as Start_Date, to_date('15-11-13', 'DD-MM-YY') as End_Date, to_date('19-10-17', 'DD-MM-YY') as Trans_Date, 200 as Revenue from dual union all
select 4 as Campaign, 2345 as Account, to_date('15-10-13', 'DD-MM-YY') as Start_Date, to_date('15-11-13', 'DD-MM-YY') as End_Date, to_date('22-05-15', 'DD-MM-YY') as Trans_Date, 300 as Revenue from dual 
;

select
   a.*
  ,case when Start_Date + (365 * 3) > Trans_Date then Revenue else null end / count(case when Start_Date + (365 * 3) > Trans_Date then 1 else null end) over (partition by account) as Avg_Revenue
from test a
order by Campaign, Account