SQL. Оператор WITH — зачем он нам? Хочу сегодня поговорить с вами про такой инструмент в написании SQL-запросов, как WITH. 💡 Что это такое? В общем и целом — это синтаксический сахар, который помогает понятным и читаемым образом получить необходимые данные из БД. Но всё по порядку. Простой пример: Допустим, у нас есть таблица sales:

id  employee_id  amount

1   101          200  
2   102          150  
3   101          100
Задача: Сколько продаж сделал каждый сотрудник, если его сумма продаж выше 200? Вот как это можно сделать с помощью WITH:

WITH sales_summary AS (
  SELECT employee_id, SUM(amount) AS total_sales
  FROM sales
  GROUP BY employee_id
)
SELECT employee_id, total_sales
FROM sales_summary
WHERE total_sales > 200;
Что произошло? Создана временная таблица sales_summary при помощи WITH, которую дальше можно использовать как обычную. А можно было проще? Да! Для этой задачи, честно говоря, можно было бы обойтись без WITH, и использовать HAVING:

SELECT employee_id, SUM(amount) AS total_sales
FROM sales
GROUP BY employee_id
HAVING SUM(amount) > 200;
🔎 Но цель была — показать, как работает WITH, а не сделать самый короткий запрос. Когда WITH реально раскрывается: Представим чуть более сложную задачу: Найти продажи по сотрудникам, затем взять топ-3 по сумме.

WITH sales_summary AS (
  SELECT employee_id, SUM(amount) AS total_sales
  FROM sales
  GROUP BY employee_id
)
SELECT *
FROM sales_summary
ORDER BY total_sales DESC
LIMIT 3;
🎯 Здесь HAVING уже не поможет — он не умеет работать с ORDER BY и LIMIT после агрегации. А с WITH — всё наглядно и читаемо. А насколько WITH затратный для базы? Хороший вопрос. На практике, в PostgreSQL WITH раньше (до версии 12) всегда материализовался — сначала считался полностью, а потом уже использовался. Сейчас ситуация лучше — запрос может быть встроен обратно (inlined), если это безопасно. 💬 Так что да, иногда может быть небольшое ухудшение производительности. Но чаще — это не критично, особенно если ты выигрываешь в читаемости и логике. Когда WITH реально полезен: 1. Когда агрегат нужно переиспользовать в другом контексте (например, джойнить с другой таблицей) 2. Когда нужно сгруппировать данные, а потом делать с ними дополнительные действия 3. Когда запрос сложный, и хочется разбить его на понятные части 4. Когда есть несколько уровней агрегации Всем добра! #sql #sql_with