← Назад к вопросам

Как работает group by?

1.0 Junior🔥 141 комментариев
#Базы данных и SQL

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI26 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

GROUP BY в SQL

GROUP BY — оператор для группировки строк по одному или нескольким столбцам и применения агрегатных функций. Это мощный инструмент для анализа данных.

Базовый синтаксис

SELECT column1, COUNT(*) as count
FROM table_name
GROUP BY column1;

Как работает GROUP BY

Пример: подсчет заказов по пользователям

SELECT user_id, COUNT(*) as order_count
FROM orders
GROUP BY user_id;

Результат:

user_id | order_count
--------|------------
1       | 5
2       | 3
3       | 7

Sistem групирует все строки по user_id, потом считает количество в каждой группе.

Пример 2: Сумма по категориям

SELECT category, SUM(price) as total_price
FROM products
GROUP BY category;

Результат:

category  | total_price
----------|------------
Electric  | 5000
Books     | 200
Clothing  | 800

Агрегатные функции с GROUP BY

  • COUNT() — количество строк
  • SUM() — сумма значений
  • AVG() — среднее значение
  • MIN() — минимальное
  • MAX() — максимальное

Пример:

SELECT 
  department,
  COUNT(*) as employee_count,
  AVG(salary) as avg_salary,
  MIN(salary) as min_salary,
  MAX(salary) as max_salary
FROM employees
GROUP BY department;

GROUP BY по нескольким столбцам

SELECT 
  country, 
  city, 
  COUNT(*) as user_count
FROM users
GROUP BY country, city;

Результат группирует по комбинации country+city.

HAVING — фильтрация групп

WHERE фильтрует строки ДО группировки. HAVING фильтрует группы ПОСЛЕ группировки.

SELECT 
  category,
  COUNT(*) as product_count
FROM products
GROUP BY category
HAVING COUNT(*) > 5;

Вернет только категории с более чем 5 товарами.

Порядок применения

  1. FROM — выбираем таблицу
  2. WHERE — фильтруем строки
  3. GROUP BY — группируем
  4. HAVING — фильтруем группы
  5. SELECT — выбираем столбцы
  6. ORDER BY — сортируем
  7. LIMIT — ограничиваем количество

Пример:

SELECT 
  department,
  AVG(salary) as avg_salary
FROM employees
WHERE hire_date > 2020-01-01        -- (2) WHERE
GROUP BY department                   -- (3) GROUP BY
HAVING AVG(salary) > 5000             -- (4) HAVING
ORDER BY avg_salary DESC              -- (6) ORDER BY
LIMIT 10;                             -- (7) LIMIT

Частые ошибки

Ошибка 1: Столбец не в GROUP BY

-- ОШИБКА!
SELECT name, department, COUNT(*)
FROM employees
GROUP BY department;  -- name НЕ в GROUP BY!

-- Правильно:
SELECT department, COUNT(*)
FROM employees
GROUP BY department;

Ошибка 2: Использовать WHERE вместо HAVING

-- ОШИБКА!
SELECT category, COUNT(*)
FROM products
WHERE COUNT(*) > 5      -- Нельзя в WHERE!
GROUP BY category;

-- Правильно:
SELECT category, COUNT(*)
FROM products
GROUP BY category
HAVING COUNT(*) > 5;    -- В HAVING!

Для QA инженера

При тестировании API с группировкой:

GET /api/v1/analytics/sales?group_by=category&aggregate=sum&field=amount

Проверяю:

  1. Результаты действительно группируются
  2. Суммы считаются правильно
  3. Все категории присутствуют
  4. Нет дубликатов
  5. NULL значения обработаны корректно

Оконные функции (Window Functions)

Это более мощная альтернатива GROUP BY:

SELECT 
  name,
  salary,
  department,
  AVG(salary) OVER (PARTITION BY department) as dept_avg
FROM employees;

Это вернет каждого сотрудника И среднюю зарплату в его отделе.

Практический пример

-- Найти топ 5 категорий по количеству продаж
SELECT 
  p.category,
  COUNT(o.id) as sale_count,
  SUM(o.amount) as total_revenue
FROM orders o
JOIN products p ON o.product_id = p.id
WHERE o.created_at > 2024-01-01
GROUP BY p.category
HAVING COUNT(o.id) > 10
ORDER BY total_revenue DESC
LIMIT 5;

GROUP BY — один из самых часто используемых SQL операторов. Необходим для анализа и отчетности.