我有一张非常大的桌子,每年有多年的快照,显示每天的数据。为了便于说明,该表看起来像这样:
Part Qty Snapshot
---- ---- --------
A 5 1/1/2015
B 10 1/1/2015
A 5 1/2/2015
B 10 1/2/2015
A 6 1/3/2015
B 10 1/3/2015
A 5 1/4/2015
B 10 1/4/2015
我想实现一个缓慢变化的数据方法,并将这些数据折叠成一个看起来像这样的形式(假设当前日期是1/4/15)
Part Qty From Thru Active
---- ---- -------- -------- ------
A 5 1/1/2015 1/2/2015 I
B 10 1/1/2015 1/4/2015 A
A 6 1/3/2015 1/3/2015 I
A 5 1/4/2015 1/4/2015 A
我有一个每天运行的功能,因此当我捕获最新的快照时,我将其转换为此方法。一旦数据实际加载到具有活动标志“C”(当前)的表中,该函数将从巨型表(实际上在DB2中)中运行。
这对我来说是有用的(一旦我加载了所有过去的日期),但是我希望有一种方法可以一次性完成所有现有日期,并将各个快照日期转换为范围。 / p>
对于它的价值,我当前的方法是为每个可能的日期值运行此函数。虽然它正在工作,但它很慢,而且我有几年的历史可以处理,因为我一次循环一天。
表:
create table main.history (
part varchar(25) not null,
qty integer not null,
from_date date not null,
thru_date date not null,
active_flag char(1)
);
create table stage.history as select * from main.history where false;
create table partitioned.history_active (
constraint history_active_ck1 check (active_flag in ('A', 'C'))
) inherits (main.history);
create table partitioned.history_inactive (
constraint history_active_ck1 check (active_flag = 'I')
) inherits (main.history);
处理一天新数据的功能:
CREATE OR REPLACE FUNCTION main.capture_history(new_date date)
RETURNS null AS
$BODY$
DECLARE
rowcount integer := 0;
BEGIN
-- partitioned.history_active already has a current snapshot for new_date
truncate table stage.history;
insert into stage.history
select
part, qty,
min (from_date), max (thru_date),
case when max (thru_date) = new_date then 'A' else 'I' end
FROM
partitioned.history_active
group by
part_qty;
truncate table partitioned.history_active;
insert into partitioned.history_active
select * from stage.history
where active_flag = 'A';
insert into partitioned.history_inactive
select * from stage.history
where active_flag = 'I';
END;
$BODY$
LANGUAGE plpgsql VOLATILE
COST 100;