Запрос для нарастающего итога
Запрос для нарастающего итога
Здраствуйте, уважаемые спецы.
Сервер FB 1.5.
В таблице есть 3 поля:
Id - первичный ключ (INTEGER),
DateDoc - дата документа (DATE),
Value - значение (INTEGER).
Нужно сделать запрос (procedure или view), в котором в 4-ом поле будет значение поля Value наростающим итогом за месяц. Кто-нибуть сталкивался с такой задачей?
Сервер FB 1.5.
В таблице есть 3 поля:
Id - первичный ключ (INTEGER),
DateDoc - дата документа (DATE),
Value - значение (INTEGER).
Нужно сделать запрос (procedure или view), в котором в 4-ом поле будет значение поля Value наростающим итогом за месяц. Кто-нибуть сталкивался с такой задачей?
-
- Заслуженный разработчик
- Сообщения: 1436
- Зарегистрирован: 15 сен 2005, 09:05
так?
Код: Выделить всё
select
...,
(select sum(t2.value) from some_table t2 where
(extract(year from t1.datedoc) = extract(year from t2.datedoc))
and (extract(month from t1.datedoc) = extract(month from t2.datedoc))
and (t2.datedoc < t1.date_doc))
from
some_table t1
Можешь добавить в таблицы документов поле периода. Тип INTEGER, структура - YYYYMM. Зависит от DateDoc и обновляется либо на клиенте либо в триггере. Позволяет существенно упростить выборку по месяцу и группировку по нему же:
вместо
и
получаем
и
Ну и плюс прирост скорости выполнения.
вместо
Код: Выделить всё
WHERE DATEDOC BETWEEN '01.12.2007' AND '31.12.2007'
Код: Выделить всё
GROUP BY EXTRACT(YEAR FROM DATEDOC), EXTRACT(MONTH FROM DATEDOC)'
Код: Выделить всё
WHERE ID_PERIOD = 200712
Код: Выделить всё
GROUP BY ID_PERIOD
-
- Сообщения: 52
- Зарегистрирован: 28 сен 2007, 10:19
А может что-нибудь типа этого?
Код: Выделить всё
select
ip.fio_spi as pristav,
case when extract(month from current_timestamp) >= 1 then sum(case when ip.date_ip_in < '01.02.2007' then 1 else 0 end) else 0 end as january,
case when extract(month from current_timestamp) >= 2 then sum(case when ip.date_ip_in < '01.03.2007' then 1 else 0 end) else 0 end as february,
case when extract(month from current_timestamp) >= 3 then sum(case when ip.date_ip_in < '01.04.2007' then 1 else 0 end) else 0 end as march,
case when extract(month from current_timestamp) >= 4 then sum(case when ip.date_ip_in < '01.05.2007' then 1 else 0 end) else 0 end as april,
case when extract(month from current_timestamp) >= 5 then sum(case when ip.date_ip_in < '01.06.2007' then 1 else 0 end) else 0 end as may,
case when extract(month from current_timestamp) >= 6 then sum(case when ip.date_ip_in < '01.07.2007' then 1 else 0 end) else 0 end as juny,
case when extract(month from current_timestamp) >= 7 then sum(case when ip.date_ip_in < '01.08.2007' then 1 else 0 end) else 0 end as july,
case when extract(month from current_timestamp) >= 8 then sum(case when ip.date_ip_in < '01.09.2007' then 1 else 0 end) else 0 end as august,
case when extract(month from current_timestamp) >= 9 then sum(case when ip.date_ip_in < '01.10.2007' then 1 else 0 end) else 0 end as september,
case when extract(month from current_timestamp) >= 10 then sum(case when ip.date_ip_in < '01.11.2007' then 1 else 0 end) else 0 end as october,
case when extract(month from current_timestamp) >= 11 then sum(case when ip.date_ip_in < '01.12.2007' then 1 else 0 end) else 0 end as november,
case when extract(month from current_timestamp) >= 12 then sum(case when ip.date_ip_in < '01.01.2008' then 1 else 0 end) else 0 end as december
from ip
group by 1
Нет, спасибо. Насколько я понял, у Вас выводится поле - название месяца и подсчитывается колличество чего-то там за месяц. Немного не то. Уважаемый CyberMax предложил хороший работающий вариант. Я сделал эту задачу при помощи процедур, но предложеный вариант элегантней.
Код: Выделить всё
CREATE PROCEDURE P_GAS
returns (
id integer,
data date,
fisher integer
)
as
declare variable vYear integer;
declare variable vMonth integer;
begin
total = 0;
vYear = 0;
vMonth = 0;
for
select id,
data,
fisher
from gas
order by data
into :id,
:data,
:fisher
do
begin
if ((EXTRACT(year from data) <> vYear) or (EXTRACT(month from data) <> vMonth)) then
begin
total = 0;
vYear = EXTRACT(year from data);
vMonth = EXTRACT(month from data);
end
total = total + :fisher;
suspend;
end
end