← К списку уроков
SQL·Лёгкий·8 мин

NULL и работа с пропусками в SQL

COALESCE, IS NULL, NULLIF — как корректно обрабатывать пропуски в данных.

NULL и работа с пропусками в SQL

NULL — отсутствие значения. Не ноль, не пустая строка — именно отсутствие. И с ним связано большинство ошибок junior-аналитиков.

NULL ≠ NULL

SELECT NULL = NULL;          -- результат NULL, не TRUE!
SELECT NULL = 5;             -- NULL
SELECT 5 = 5;                -- TRUE

NULL любая операция с обычным значением → NULL. Нельзя сравнить через =.

IS NULL и IS NOT NULL

Единственный правильный способ проверить:

WHERE col IS NULL
WHERE col IS NOT NULL

Никогда не пиши WHERE col = NULL — всегда вернёт пустоту.

COALESCE — замена NULL на значение

SELECT
    name,
    COALESCE(email, 'no-email') AS email_or_default
FROM users;

COALESCE(a, b, c) возвращает первый не-NULL аргумент. Цепочка для приоритетов:

COALESCE(phone, whatsapp, telegram, 'нет контакта')

NULLIF — обратное преобразование

SELECT NULLIF(salary, 0);   -- 0 → NULL

Полезно для деления:

SELECT total / NULLIF(count, 0)    -- если count = 0, результат NULL, не ошибка

NULL в агрегатах

ФункцияПоведение
COUNT(*)считает все строки
COUNT(col)игнорирует NULL
SUM(col)игнорирует NULL
AVG(col)игнорирует NULL (важно!)
MIN(col), MAX(col)игнорируют NULL
-- На 100 строках, 30 NULL в `salary`:
SELECT
    COUNT(*) AS total,             -- 100
    COUNT(salary) AS with_salary,  -- 70
    AVG(salary) AS avg_salary      -- среднее по 70 строкам, не по 100!
FROM employees;

LEFT JOIN + IS NULL — anti-join

Найти пользователей без заказов:

SELECT u.id, u.name
FROM users u
LEFT JOIN orders o ON o.user_id = u.id
WHERE o.id IS NULL;

Классический паттерн "что есть в A, чего нет в B".

NULL в GROUP BY

NULL формирует свою отдельную группу:

SELECT city, COUNT(*) FROM users GROUP BY city;
-- 'Алматы' | 100
-- 'Астана' | 80
-- NULL     | 20    <-- юзеры без города

Что важно запомнить

  • IS NULL / IS NOT NULL — единственный правильный способ проверки
  • COALESCE — твой друг для дефолтов
  • NULLIF(x, 0) — защита от деления на ноль
  • AVG() считает только не-NULL строки → это часто не то что нужно
  • На собеседовании: «что вернёт SELECT NULL = NULL» — частый вопрос
  • В коде модели: NULL = "мы не знаем", не "ничего"