← К оглавлению занятия

Занятие 26. Табличные выражения

📁 Блок: SQL / MySQL / Подзапросы и CTE ⏱️ Время изучения: ~75 мин 🎯 Сложность: Средняя
#as #select #from

⚡ Кратко: типичные ошибки

  • Использование имени CTE напрямую в IN без скобочного SELECT.
  • Отсутствие скобок вокруг определения CTE.
  • Попытка использовать CTE в следующем запросе — он доступен только в текущем.

🐛 Типичные ошибки и исправления

Ошибка 1. Использование CTE как таблицы без скобочного SELECT

Неправильно:

WITH la_clients AS (
    SELECT id FROM customers WHERE city = 'Los Angeles'
)
SELECT * FROM orders
WHERE customer_id IN la_clients;

Почему плохо: la_clients — это имя CTE, а не таблица, которую можно указать прямо в IN. Нужно явно выбрать столбец из CTE.

Правильно:

WITH la_clients AS (
    SELECT id FROM customers WHERE city = 'Los Angeles'
)
SELECT * FROM orders
WHERE customer_id IN (SELECT id FROM la_clients);

Ошибка 2. Пропуск скобок в определении CTE

Неправильно:

WITH avg_price AS
    SELECT AVG(unit_price) AS ap FROM order_details
SELECT * FROM order_details
WHERE unit_price > (SELECT ap FROM avg_price);

Правильно:

WITH avg_price AS (
    SELECT AVG(unit_price) AS ap FROM order_details
)
SELECT * FROM order_details
WHERE unit_price > (SELECT ap FROM avg_price);

Ошибка 3. Обращение к CTE из другого запроса

Неправильно:

WITH avg_price AS (
    SELECT AVG(unit_price) AS ap FROM order_details
)
SELECT * FROM order_details WHERE unit_price > (SELECT ap FROM avg_price);

SELECT * FROM order_details WHERE unit_price < (SELECT ap FROM avg_price);

Почему плохо: CTE существует только в рамках одного запроса. Второй SELECT не видит avg_price.

Правильно: объединить логику в один запрос или повторить определение CTE.

Ошибка 4. Путаница между CTE и временной таблицей

CTE не сохраняет данные на диск и не видна в других сессиях. Если нужно переиспользовать результат между разными запросами, используйте временную таблицу CREATE TEMPORARY TABLE.