SELECT generate_series(1, 5) AS n;
Результат:
n -- 1 2 3
SELECT generate_series(
DATE '2026-07-01',
DATE '2026-07-31',
INTERVAL '1 day'
)::date AS day;
Результат:
day ---------- 2026-07-01 2026-07-02 2026-07-03
SELECT d::date AS day,
COUNT(o.id) AS orders
FROM generate_series(
CURRENT_DATE - INTERVAL '6 days',
CURRENT_DATE,
INTERVAL '1 day'
) AS d
LEFT JOIN orders o
ON o.created_at::date = d::date
GROUP BY 1
ORDER BY 1;
Результат:
day | orders -----------+------- 2026-07-05 | 12 2026-07-06 | 0 2026-07-07 | 19Порешать SQL-задачи в тренажёре →
Спрашивают, когда нужно построить календарь/ось дат и заполнить пропущенные периоды; в паре с LEFT JOIN, DATE_TRUNC и агрегатами (COUNT/SUM).
В SQLite есть табличная функция generate_series(), но только для чисел и лишь если соответствующий модуль включён в сборку — версии для дат нет. В MySQL функции нет совсем: ряд строят рекурсивным CTE (WITH RECURSIVE dates AS (...)). Полноценно, включая даты, GENERATE_SERIES работает в PostgreSQL.
Сгенерируйте ряд дат через generate_series(start, stop, INTERVAL '1 day') и сделайте LEFT JOIN к таблице с данными по дате. Дни без записей дадут NULL, а COUNT(...) по ним вернёт 0. Так в отчёте не будет разрывов в оси времени.
Да. Для чисел работает дробный шаг: generate_series(0, 1, 0.25). Для времени шаг задаётся интервалом: generate_series(ts1, ts2, INTERVAL '1 hour') построит ряд по часам. Главное — знак шага должен вести от start к stop, иначе строк не будет.
LAG · date_trunc · EXTRACT · STRING_AGG · COUNT · SUM OVER
Открыть SQL-тренажёр (565 задач) →