Перейти к содержанию
SQLJunior≈ 20 минутУчебная задача HireHero

Доля покупателей с повторным заказом

У интернет-магазина есть выгрузка заказов за сентябрь. Команда хочет понять, сколько покупателей вернулись за второй покупкой в том же месяце.

Условие

Найди число покупателей с хотя бы одним оплаченным заказом, число покупателей с двумя и более оплаченными заказами и долю второй группы в первой. Отменённые заказы не считаются. Один order_id — один заказ; таблица не содержит дублей. Доля должна быть в процентах с двумя знаками после запятой.

Данные

order_iduser_idstatusamount
1101paid1200
2101paid800
3102paid500
4103paid2000
5103paid700
6104paid900
7105cancelled1500

Все данные учебные. Код можно выполнить в своей среде; поле ниже предназначено для черновика, без запуска кода.

Черновик сохраняется в этом браузере. Ничего не отправляется на сервер.

Если нужен следующий шаг

Подсказка 1
Сначала оставь оплаченные заказы и собери по одной строке на покупателя.
Подсказка 2
Знаменатель — все покупатели из полученной таблицы. HAVING COUNT(*) >= 2 до расчёта знаменателя потеряет покупателей с одной покупкой.

Проверь себя

Показать решение и объяснение
4 покупателя, из них 2 повторных. Доля повторных покупателей — 50,00%. Выручка здесь не влияет на определение повторной покупки.
SQL · SQLite / PostgreSQL
WITH buyers AS (
  SELECT user_id, COUNT(*) AS orders_count
  FROM orders
  WHERE status = 'paid'
  GROUP BY user_id
)
SELECT COUNT(*) AS buyers,
       SUM(CASE WHEN orders_count >= 2 THEN 1 ELSE 0 END) AS repeat_buyers,
       ROUND(100.0 * SUM(CASE WHEN orders_count >= 2 THEN 1 ELSE 0 END)
             / NULLIF(COUNT(*), 0), 2) AS repeat_share_pct
FROM buyers;

Два уровня агрегации отвечают на два разных вопроса: сколько заказов у человека и сколько таких людей в базе. Множитель 100.0 сохраняет дробную часть; NULLIF защищает от деления на ноль. В пустой выборке доля будет NULL: это отсутствие наблюдений, а не нулевая повторная покупка.

Проверка решения

  • Покупатель 105 исключён вместе с отменённым заказом.
  • Покупатели 102 и 104 остаются в знаменателе.
  • При отсутствии оплаченных заказов запрос не делит на ноль.

Вопрос на продолжение

Как изменится расчёт, если считать вторую покупку за всю историю, а не внутри месяца? Какие поля понадобятся для повторной покупки в течение 30 дней?