DISTINCT и GROUP BY для уникальности
Узнайте, когда правильный ответ — DISTINCT, а когда на собеседовании ожидают GROUP BY.
«DISTINCT и GROUP BY для уникальности» — бесплатный урок SQL Interview Prep на CoddyKit. Это урок 3 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения SQL Interview Prep, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс SQL Interview Prep содержит 4 уроков всего.
Что делает DISTINCT
DISTINCT удаляет дублирующиеся строки. Главное, что проверяют на собеседованиях: он работает со всей выбранной строкой, а не с одним столбцом, поэтому SELECT DISTINCT a, b устраняет дубликаты пары (a, b).
SELECT DISTINCT department
FROM employees;DISTINCT охватывает все выбранные столбцы
Если столбцов несколько, DISTINCT сохраняет каждую уникальную комбинацию — по одной строке для каждой уникальной пары (department, job_title). Стандартного способа устранить дубликаты только в одном столбце нет.
SELECT DISTINCT department, job_title
FROM employees;Что делает GROUP BY
GROUP BY объединяет строки с одинаковым ключом в одну строку на группу. Само по себе группирование по столбцу даёт тот же результат, что и DISTINCT для этого столбца.
SELECT department
FROM employees
GROUP BY department;
-- equivalent to:
SELECT DISTINCT department
FROM employees;Главное различие: агрегация
В чём же разница? В необходимости использовать агрегатную функцию. GROUP BY может вычислять COUNT, SUM или AVG для каждой группы, а DISTINCT не может. Нужны уникальные строки? DISTINCT. Нужна метрика для каждой группы? GROUP BY.
SELECT department, COUNT(*) AS headcount
FROM employees
GROUP BY department;DISTINCT не умеет считать по группам
Нельзя просто добавить подсчёт к DISTINCT. Для задачи «сколько сотрудников в каждом отделе» всегда используйте GROUP BY с COUNT(*) — не SELECT DISTINCT.
-- WRONG intent: this errors or returns one total row
-- SELECT DISTINCT department, COUNT(*) FROM employees;
-- RIGHT:
SELECT department, COUNT(*) AS headcount
FROM employees
GROUP BY department;COUNT(DISTINCT) объединяет оба подхода
Популярное сочетание: COUNT(DISTINCT col) подсчитывает уникальные значения внутри каждой группы. Здесь DISTINCT находится внутри агрегатной функции и отвечает на вопрос «сколько уникальных должностей в каждом отделе?»
SELECT department,
COUNT(DISTINCT job_title) AS distinct_titles
FROM employees
GROUP BY department;Подсчёт уникальных значений в целом
Без GROUP BY COUNT(DISTINCT col) подсчитывает уникальные значения во всей таблице — это простой ответ на вопрос «сколько разных отделов у нас есть?»
SELECT COUNT(DISTINCT department) AS n_departments
FROM employees;
-- equivalently, count the deduped subquery
SELECT COUNT(*)
FROM (SELECT DISTINCT department FROM employees) d;Производительность часто не различается
Что быстрее: DISTINCT или GROUP BY? Для обычного устранения дубликатов они обычно эквивалентны — оптимизаторы строят для них похожие планы. Выбирайте по смыслу: DISTINCT — для уникальных строк, GROUP BY — для агрегации.
DISTINCT и NULL
Как DISTINCT обрабатывает NULL? Он считает все значения NULL одинаковыми, поэтому множество строк с NULL объединяется в одну. GROUP BY делает то же самое: значения NULL образуют одну группу.
-- If manager_id has several NULLs, this returns one NULL row
SELECT DISTINCT manager_id
FROM employees;Postgres DISTINCT ON (дополнение)
Дополнение: в Postgres есть нестандартная конструкция DISTINCT ON (expr), которая сохраняет первую строку для каждого ключа согласно ORDER BY. Переносимый код использует ROW_NUMBER() вместо неё.
-- Postgres only: latest order per customer
SELECT DISTINCT ON (customer_id) customer_id, order_id, order_date
FROM orders
ORDER BY customer_id, order_date DESC;DISTINCT применяется ко всему SELECT, а не к одному столбцу
Ещё одна ловушка: DISTINCT работает со всей строкой, поэтому SELECT DISTINCT customer_id, order_date не вернёт по одной строке на клиента. Для этого используйте GROUP BY с MAX или оконную функцию.
-- Does NOT give one row per customer
SELECT DISTINCT customer_id, order_date FROM orders;
-- One row per customer: latest order date
SELECT customer_id, MAX(order_date) AS last_order
FROM orders
GROUP BY customer_id;Быстрая проверка
Выберите подходящий инструмент.
Итоги
Итак: DISTINCT устраняет дубликаты целых строк; GROUP BY объединяет строки по ключу и поддерживает агрегатные функции. COUNT(DISTINCT col) подсчитывает уникальные значения, оба подхода считают NULL одной группой, а производительность обычно не различается.
Часто задаваемые вопросы
Урок «DISTINCT и GROUP BY для уникальности» бесплатный?
Да — полный текст урока «DISTINCT и GROUP BY для уникальности» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс SQL Interview Prep, подпишись на CoddyKit PRO. Курс SQL Interview Prep содержит 4 уроков всего.
Чему я научусь в уроке «DISTINCT и GROUP BY для уникальности»?
Узнайте, когда правильный ответ — DISTINCT, а когда на собеседовании ожидают GROUP BY. Ты практикуешь SQL Interview Prep с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.
Нужен ли мне опыт, чтобы начать SQL Interview Prep?
Предыдущий опыт не требуется. SQL Interview Prep на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 3 из 4.
Сколько времени занимает урок «DISTINCT и GROUP BY для уникальности»?
Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.
Можно ли писать и запускать код в этом уроке SQL Interview Prep?
Да. Каждый урок SQL Interview Prep включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.
Все уроки этого курса
- Выбор столбцов и подводные камни псевдонимов
- Вычисляемые столбцы и приоритет выражений
- DISTINCT и GROUP BY для уникальности
- Выражения CASE в SELECT