Voici une approche alternative qui nécessite LAG() qui est disponible à partir de SQL 2012, mais notez que les exemples de données ne contiennent pas "28 jours distincts" avant chaque date. De plus, le type de données réel utilisé n'est pas connu (date/smalldatetime/datetime/datetime2) et on ne sait pas non plus si la troncation de l'heure à partir de la date est nécessaire. Donc, avec quelques mises en garde, cette approche crée une série de plages de dates pour les 28 dates distinctes (mais si les données ne les fournissent pas, alors ce sont 28 jours écoulés). Voici une démo sqlfiddle
Configuration du schéma PostgreSQL 9.3 :(car SQL Server ne fonctionne pas sur sqlfiddle)
CREATE TABLE Table1
(theDate timestamp, Value int, promo int, item int)
;
INSERT INTO Table1
(theDate, Value, promo, item)
VALUES
('2011-01-01 00:00:00', 626, 0, 1230),
('2011-01-02 00:00:00', 231, 1, 1230),
('2011-01-03 00:00:00', 572, 1, 1230),
('2011-01-04 00:00:00', 775, 1, 1230),
('2011-01-05 00:00:00', 660, 1, 1230),
('2011-01-06 00:00:00', 662, 1, 1230),
('2011-01-07 00:00:00', 541, 1, 1230),
('2011-01-08 00:00:00', 849, 1, 1230),
('2011-01-09 00:00:00', 632, 1, 1230),
('2011-01-10 00:00:00', 906, 1, 1230),
('2011-01-11 00:00:00', 961, 1, 1230),
('2011-01-12 00:00:00', 361, 0, 1230),
('2012-01-01 00:00:00', 461, 0, 1230),
('2012-01-02 00:00:00', 928, 1, 1230),
('2012-01-03 00:00:00', 855, 0, 1230),
('2012-01-04 00:00:00', 605, 0, 1230),
('2012-01-05 00:00:00', 83, 0, 1230),
('2012-01-06 00:00:00', 44, 0, 1230),
('2012-01-07 00:00:00', 382, 0, 1230),
('2012-01-08 00:00:00', 862, 0, 1230),
('2012-01-09 00:00:00', 549, 0, 1230),
('2012-01-10 00:00:00', 632, 0, 1230),
('2012-01-11 00:00:00', 2, 0, 1230),
('2012-01-12 00:00:00', 26, 0, 1230)
;
Requête 1 :
select
t1.item
, ranges.theStart
, ranges.theEnd
, sum(t1.value)
, sum(t1.value) / 28 avg
from (
select
coalesce(lag(theDay,28) over(order by theDay) , theDay - INTERVAL '28 DAYS') as theStart
, theDay as theEnd
from (
select distinct cast(thedate as date) theDay from Table1
) days
) ranges
inner join table1 t1 on theDate between ranges.theStart and ranges.theEnd
group by
t1.item
, ranges.theStart
, ranges.theEnd
| item | thestart | theend | sum | avg |
|------|----------------------------|---------------------------|------|-----|
| 1230 | December, 04 2010 00:00:00 | January, 01 2011 00:00:00 | 626 | 22 |
| 1230 | December, 05 2010 00:00:00 | January, 02 2011 00:00:00 | 857 | 30 |
| 1230 | December, 06 2010 00:00:00 | January, 03 2011 00:00:00 | 1429 | 51 |
| 1230 | December, 07 2010 00:00:00 | January, 04 2011 00:00:00 | 2204 | 78 |
| 1230 | December, 08 2010 00:00:00 | January, 05 2011 00:00:00 | 2864 | 102 |
| 1230 | December, 09 2010 00:00:00 | January, 06 2011 00:00:00 | 3526 | 125 |
| 1230 | December, 10 2010 00:00:00 | January, 07 2011 00:00:00 | 4067 | 145 |
| 1230 | December, 11 2010 00:00:00 | January, 08 2011 00:00:00 | 4916 | 175 |
| 1230 | December, 12 2010 00:00:00 | January, 09 2011 00:00:00 | 5548 | 198 |
| 1230 | December, 13 2010 00:00:00 | January, 10 2011 00:00:00 | 6454 | 230 |
| 1230 | December, 14 2010 00:00:00 | January, 11 2011 00:00:00 | 7415 | 264 |
| 1230 | December, 15 2010 00:00:00 | January, 12 2011 00:00:00 | 7776 | 277 |
| 1230 | December, 04 2011 00:00:00 | January, 01 2012 00:00:00 | 461 | 16 |
| 1230 | December, 05 2011 00:00:00 | January, 02 2012 00:00:00 | 1389 | 49 |
| 1230 | December, 06 2011 00:00:00 | January, 03 2012 00:00:00 | 2244 | 80 |
| 1230 | December, 07 2011 00:00:00 | January, 04 2012 00:00:00 | 2849 | 101 |
| 1230 | December, 08 2011 00:00:00 | January, 05 2012 00:00:00 | 2932 | 104 |
| 1230 | December, 09 2011 00:00:00 | January, 06 2012 00:00:00 | 2976 | 106 |
| 1230 | December, 10 2011 00:00:00 | January, 07 2012 00:00:00 | 3358 | 119 |
| 1230 | December, 11 2011 00:00:00 | January, 08 2012 00:00:00 | 4220 | 150 |
| 1230 | December, 12 2011 00:00:00 | January, 09 2012 00:00:00 | 4769 | 170 |
| 1230 | December, 13 2011 00:00:00 | January, 10 2012 00:00:00 | 5401 | 192 |
| 1230 | December, 14 2011 00:00:00 | January, 11 2012 00:00:00 | 5403 | 192 |
| 1230 | December, 15 2011 00:00:00 | January, 12 2012 00:00:00 | 5429 | 193 |
NB :Pour SQL Server
- au lieu de
theDay - INTERVAL '28 DAYS'
utilisez dateadd(day,-28,theDay)