SQL выполняет один и тот же запрос несколько раз

У меня есть запрос, который дает мне COUNT между двумя датами, start_date и end_date, и сгруппирован по различным столбцам. Есть ли способ получить COUNT за каждый день? Как, скажем, start_date - это date1, а end_date - date5, поэтому мне нужно запустить запрос один раз для «date1 to date2», «date1 to date3», затем «date1 to date4», затем «date1 to date5». Как при выполнении одного и того же запроса несколько раз в зависимости от даты начала и окончания? Мой запрос выглядит так

Select COUNT(A), B, C, D
FROM TABLE 
WHERE CONDITION1 AND DATE BETWEEN start_date AND end_date
GROUP BY B, C, D

person Neha    schedule 21.04.2015    source источник
comment
Для какой СУБД это нужно? Добавьте тег, чтобы указать, используете ли вы mysql, postgresql, sql-server, oracle или db2 - или что-то совсем другое.   -  person marc_s    schedule 21.04.2015


Ответы (2)


Select COUNT(A), B, C, D,DATE 
FROM TABLE 
WHERE CONDITION1 AND DATE BETWEEN start_date AND end_date
GROUP BY B, C, D,DATE 

Добавить DATE в группу по

Если поле - datetime, используйте convert (из @ ta.speot.is: SQL Server 2005 не имеет типа DATE)

Select COUNT(A), B, C, D,convert(date,DATETime) 
    FROM TABLE 
    WHERE CONDITION1 AND DATE BETWEEN start_date AND end_date
    GROUP BY B, C, D,convert(date,DATETime) 

Добавить DATE в группу по

Отредактировано на основе OP:

declare increment int;
set increment  = 1
declare tempdate date;

set tempdate  = start_date  
while (tempdate  < end_date)


Select COUNT(A), B, C, D,DATE 
    FROM TABLE 
    WHERE CONDITION1 AND DATE BETWEEN start_date AND DATEADD(day,increment,  start_date )
    GROUP BY B, C, D,DATE 

set increment = increment   + 1
set tempdate   =  DATEADD(day,1,tempdate )
end 

вам нужно использовать цикл и сделать что-то вроде выше

person backtrack    schedule 21.04.2015
comment
Что делать, если дата недоступна в таблице, но показывает 0 по сравнению с этой датой? - person Jankya; 21.04.2015
comment
имеется в виду, что дата подачи недоступна ..? - person backtrack; 21.04.2015
comment
Если поле - datetime, используйте convert Если это важно, SQL Server 2005 не имеет типа DATE. - person ta.speot.is; 21.04.2015
comment
@Backtrack. Нет. Означает, что дата недоступна в таблице из указанного диапазона. Скажем, от даты A до даты C, дата B недоступна в таблице, но хочет показать счетчик 0 по сравнению с датой B. - person Jankya; 21.04.2015
comment
В этом случае добавьте дополнительное условие if или Isnull - person backtrack; 21.04.2015
comment
Обратите внимание, что будут синтаксические ошибки. Пожалуйста, исправьте это. Сообщите нам, если вам понадобится помощь - person backtrack; 21.04.2015
comment
@Backtrack Привет, спасибо большое! Это решает проблему, но я сомневаюсь, что это сработает для меня. Я работаю над клиентом SQL. У меня нет доступа на запись. Не могу использовать блок PL / SQL. - person Neha; 21.04.2015
comment
@Neha, ладно, рассмотрите возможность голосования и примите ответ - person backtrack; 21.04.2015

Я покажу, как я достигаю этого с помощью Oracle, а затем как то же самое можно применить к Vertica.

Я начинаю с написания запроса, чтобы получить список дат. Нравится:

select to_date('01-APR-2015','dd-mon-yyyy') + rownum -1 as begin_date
from all_objects
where rownum <= to_date('05-APR-2015','dd-mon-yyyy') - to_date('01-APR-2015','dd-mon-yyyy')+1;

Это возвращает:

01-APR-15 12:00:00 AM
02-APR-15 12:00:00 AM
03-APR-15 12:00:00 AM
04-APR-15 12:00:00 AM
05-APR-15 12:00:00 AM

Я не слишком знаком с Vertica, но похоже, что этого можно добиться с помощью этого запроса:

SELECT ts::DATE
  FROM (SELECT '04/01/2015'::TIMESTAMP as tm
        UNION
        SELECT '04/05/2015'::TIMESTAMP as tm) as t
TIMESERIES ts as '1 Day' OVER (ORDER BY tm);

(Источник: http://www.vertica-forums.com/viewtopic.php?t=1333)

Затем я использую декартово / перекрестное соединение с тем же запросом для создания диапазонов дат:

select *
from (
    select to_date('01-APR-2015','dd-mon-yyyy') + rownum -1 as begin_date
    from all_objects
    where rownum <= to_date('05-APR-2015','dd-mon-yyyy')-to_date('01-APR-2015','dd-mon-yyyy')+1
) q1, (
    select to_date('01-APR-2015','dd-mon-yyyy') + rownum -1 as end_date
    from all_objects
    where rownum <= to_date('05-APR-2015','dd-mon-yyyy')-to_date('01-APR-2015','dd-mon-yyyy')+1
) q2
where begin_date <= end_date;

Результаты выглядят так:

BEGIN_DATE              END_DATE
01-APR-15 12:00:00 AM   01-APR-15 12:00:00 AM
01-APR-15 12:00:00 AM   02-APR-15 12:00:00 AM
01-APR-15 12:00:00 AM   03-APR-15 12:00:00 AM
01-APR-15 12:00:00 AM   04-APR-15 12:00:00 AM
01-APR-15 12:00:00 AM   05-APR-15 12:00:00 AM
02-APR-15 12:00:00 AM   02-APR-15 12:00:00 AM
02-APR-15 12:00:00 AM   03-APR-15 12:00:00 AM
02-APR-15 12:00:00 AM   04-APR-15 12:00:00 AM
02-APR-15 12:00:00 AM   05-APR-15 12:00:00 AM
03-APR-15 12:00:00 AM   03-APR-15 12:00:00 AM
03-APR-15 12:00:00 AM   04-APR-15 12:00:00 AM
03-APR-15 12:00:00 AM   05-APR-15 12:00:00 AM
04-APR-15 12:00:00 AM   04-APR-15 12:00:00 AM
04-APR-15 12:00:00 AM   05-APR-15 12:00:00 AM
05-APR-15 12:00:00 AM   05-APR-15 12:00:00 AM

Если вам не нужны однодневные диапазоны (например, 01.04.2015 - 01.04.2015), просто измените begin_date ‹= end_date на begin_date‹ end_date.

После этого вы можете присоединить весь запрос к выполняемому запросу:

Select q.begin_date, q.end_date, t.B, t.C, t.D, count(t.A)
FROM tmp t, (
    select *
    from (
        select to_date('01-APR-2015','dd-mon-yyyy') + rownum -1 as begin_date
        from all_objects
        where rownum <= to_date('05-APR-2015','dd-mon-yyyy')-to_date('01-APR-2015','dd-mon-yyyy')+1
    ) q1, (
        select to_date('01-APR-2015','dd-mon-yyyy') + rownum -1 as end_date
        from all_objects
        where rownum <= to_date('05-APR-2015','dd-mon-yyyy')-to_date('01-APR-2015','dd-mon-yyyy')+1
    ) q2
    where begin_date <= end_date 
) q
where t.theDate between q.begin_date and q.end_date
group by q.begin_date, q.end_date, t.B, t.C, t.D
order by q.begin_date, q.end_date;

Вот SQLFiddle: http://sqlfiddle.com/#!4/9628d/9

Надеюсь, это поможет.

person Mark Leiber    schedule 21.04.2015