Короткий ответ
Нужно сгруппировать заказы по клиенту, посчитать количество уникальных месяцев через COUNT(DISTINCT DATE_TRUNC('month', order_date)) и отфильтровать группы, где это число больше или равно 3, через HAVING.
Как это работает подробнее
COUNT(DISTINCT ...) внутри группы считает не общее количество заказов, а число уникальных значений выражения — в данном случае уникальных «месяцев» заказа у этого клиента. HAVING затем сравнивает это число с порогом.
Пример кода
Запрос SQL
SELECT customer_id
FROM orders
GROUP BY customer_id
HAVING COUNT(DISTINCT DATE_TRUNC('month', order_date)) >= 3;Что использовать на практике
- На практике: такой запрос — простой способ отличить «активного» клиента, который возвращается в разные месяцы, от клиента, сделавшего много заказов за один день. Важно использовать именно
DATE_TRUNC(или аналог), а не простоorder_date, иначе каждая отдельная дата будет считаться отдельным «месяцем». - Результат: Результат — только клиенты с заказами в 3+ разных месяцах.
- Проверка: для одного найденного клиента вывести
SELECT DISTINCT DATE_TRUNC('month', order_date) FROM orders WHERE customer_id = ...и убедиться, что их действительно 3 или больше.
Подводные камни
- Частая ошибка: считают
COUNT(DISTINCT order_date)вместоCOUNT(DISTINCT DATE_TRUNC('month', order_date))— это покажет число уникальных дней, а не месяцев, что отвечает на другой вопрос; не осознают, что клиент с заказами в январе 2023 и январе 2024 — это 2 разных месяца, а не один.