Ответ вслух Middle JOIN обновлено

Сумма в отчёте задвоилась

Вопрос

После доработки отчёта сумма выручки по клиентам выросла примерно вдвое, хотя данные не менялись. Как будешь искать причину и как исправишь?

Попробуйте сами

Ответьте вслух за 2 минуты, как на собесе. Потом сверьтесь с тезисами: что прозвучало, а что нет.

Показать ответ и разбор

Коротко

Почти всегда такое значит, что JOIN размножил строки. Я бы посмотрел, что поменялось в запросе: скорее всего добавилась таблица со связью один ко многим, например отзывы или адреса клиента.

Что должно прозвучать в ответе

  • Первая гипотеза: новый JOIN со связью один ко многим размножил строки

  • Проверка: сравнить COUNT(*) и COUNT(DISTINCT order_id) до и после JOIN

  • Найти таблицу, где на один ключ приходится несколько строк (GROUP BY key HAVING COUNT(*) > 1)

  • Исправление: агрегировать каждую ветку отдельно в подзапросе или CTE и соединять уже агрегаты

  • Альтернатива: заменить JOIN на EXISTS, если из второй таблицы нужен только факт наличия

  • Добавить тест или проверку сверки итогов с эталоном

Что могут спросить следом

  • Почему SUM(DISTINCT total) не лучшее исправление?
  • Как бы ты написал запрос, если нужны и выручка, и число отзывов?

Разбор

Почти всегда такое значит, что JOIN размножил строки. Я бы посмотрел, что поменялось в запросе: скорее всего добавилась таблица со связью один ко многим, например отзывы или адреса клиента. Проверяю: считаю COUNT(*) и COUNT(DISTINCT order_id) до и после нового JOIN; если они разошлись, заказ встречается несколько раз. Потом нахожу, где на ключ приходится несколько строк, через GROUP BY ключ HAVING COUNT(*) > 1. Исправление: агрегирую каждую ветку отдельно, выручку по клиенту в одном CTE, отзывы в другом, и соединяю уже по одной строке на клиента. Если из второй таблицы нужен только факт наличия, достаточно EXISTS. SUM(DISTINCT total) не подходит: он склеит два разных заказа с одинаковой суммой. И на будущее добавил бы сверку итога отчёта с простым контрольным запросом.

Ответьте сами, а не прочитайте

В тренажёре вопрос попадёт в повторения и вернётся, когда начнёт забываться. Плюс билеты с зачётом: 20 вопросов, не больше 2 ошибок.

Термины по теме