我正在为以下问题寻找性能良好的解决方案:
我有两张桌子
我想要做的第一件事是在事件发生前5天或更短的时间内选择所有值到一个单独的表中,并填写eventNumber和daysBeforeEvent的列
| eventNumber| dayBeforeEv | value |
|:-----------|------------:|:------------:|
| 1 | 1 | -1 |
| 1 | 2 | 21 |
| 1 | 3 | 15 |
| 1 | 4 | 7 |
| 1 | 5 | -7 |
| 2 | 1 | -9 |
| 2 | 2 | 12 |
| 2 | 3 | 1 |
| 2 | 4 | -7 |
| 2 | 5 | 8 |
| 3 | 1 | 18 |
| ... | ... | ... |
在第二个表中,我想选择同一结构中事件之间的时间的所有值。我想在这里使用一种滑动窗口。
Day |1 |2 |3 |4 |5 |6 |7 |8 |9 |10 |
Event |X | | | | | | | | |X |
第一个窗口将从第2天到第6天 然后窗口将移动一天,第二个窗口将从第3天到第7天等。 如果有一个事件,窗口会变短,例如从第6天到第9天(4天,下一个将只包括3天)
我现在使用以下解决方案:
DECLARE @cnt INT = 1;
WHILE @cnt <= 5
BEGIN
INSERT INTO "RESULT" ("EVENT_NUM","EVENT_ID","VALUE","DATE")
SELECT ROW_NUMBER() OVER (ORDER BY "DATE" ASC) AS ROW,@cnt,"VALUE","DATE" FROM "TEMP_TABLE"
WHERE "DATE" IN (SELECT DATEADD(day,@cnt*-1,"DATE") FROM "EVENT" ORDER BY "DATE" ASC);
SET @cnt = @cnt + 1;
END;
在TEMP_Table中没有日期缺失之前,它可以正常工作。但是当存在差距时(例如我在2016-02-01和2016-02-03进入,因此缺少2016-02-02)
答案 0 :(得分:0)
请修改此伪答案以向我们显示所需的结果。我认为它涵盖了你问题的第一部分,但是&#34;窗口&#34;第二部分仍不清楚。
declare @Event table (EventId int primary key, EventDate datetime, EventDesc varchar(100));
insert into @Event
select 1, '2015-10-15', 'Event 1' union all
select 2, '2015-11-15', 'Event 2'
declare @Temp table (TempDate datetime primary key, TempValue int);
insert into @Temp
select '2015-10-12', -1 union all
select '2015-10-11', 21 union all
select '2015-11-14', 14
declare @Numbers table (N int primary key);
insert into @Numbers
select 1 union all
select 2 union all
select 3 union all
select 4 union all
select 5;
with stage as
( select EventId,
EventDate,
EventDesc,
[DaysBeforeEv] = n.n-1,
[ThisDate] = dateadd(day, -(n.n-1), EventDate)
from @Event
cross
apply @Numbers n
where n.n <= 5
)
select *
from stage s
left
join @Temp t on
s.ThisDate = t.TempDate
order
by s.EventId, s.ThisDate desc