0Pricing
SQL Academy · Урок

IS NULL и IS NOT NULL

Правильно проверяйте отсутствующие значения

«IS NULL и IS NOT NULL» — бесплатный урок SQL Academy на CoddyKit. Это урок 2 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения SQL Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс SQL Academy содержит 4 уроков всего.

Проверка отсутствующих значений

Поскольку сравнения с NULL всегда возвращают неизвестный результат, SQL предоставляет два специальных оператора для проверки отсутствующих значений: IS NULL и IS NOT NULL.

Это единственный надёжный способ находить значения NULL или исключать их. В этом уроке вы научитесь правильно ими пользоваться.

-- Rows where phone is missing
SELECT name FROM customers WHERE phone IS NULL;

-- Rows where phone is present
SELECT name FROM customers WHERE phone IS NOT NULL;

Почему = NULL не работает

Соблазнительно написать WHERE phone = NULL, но такое условие никогда ни с чем не совпадает. Для каждой строки оно даёт результат unknown, а WHERE сохраняет только строки с результатом истина.

В результате получается пустой набор — незаметная ошибка, поскольку сообщение об ошибке не появляется.

-- Always returns 0 rows, even if NULLs exist
SELECT * FROM customers WHERE phone = NULL;

-- The fix
SELECT * FROM customers WHERE phone IS NULL;

IS NULL в действии

IS NULL возвращает true ровно тогда, когда значение отсутствует, и false в противном случае. Этот оператор никогда не возвращает unknown.

Поэтому его безопасно использовать везде, где нужен однозначный результат true/false.

SELECT id, name, (phone IS NULL) AS missing_phone
FROM customers;

-- id | name  | missing_phone
-- ---+-------+--------------
--  1 | Alice | f
--  2 | Bob   | t
--  3 | Carol | t

IS NOT NULL в действии

IS NOT NULL — полная противоположность: true, когда значение присутствует, и false, когда оно отсутствует.

Используйте его, чтобы отфильтровать строки, в которых действительно есть данные, например клиентов, которым можно позвонить.

SELECT name, phone
FROM customers
WHERE phone IS NOT NULL;

-- name  | phone
-- ------+----------
-- Alice | 555-0101

Объединение с AND / OR

Проверки NULL можно объединять с другими условиями с помощью AND и OR.

Например, можно найти активных клиентов, которым всё ещё нужно указать номер телефона в записи, — это распространённый запрос для проверки качества данных.

SELECT id, name
FROM customers
WHERE is_active = true
  AND phone IS NULL;

-- Active customers missing a phone number

NULL в NOT IN: ловушка

NOT IN ведёт себя неожиданно, если список содержит NULL. Если в наборе есть хотя бы одно значение NULL, NOT IN может вернуть unknown для каждой строки и отбрасывать результаты, которые вы ожидали получить.

Отдавайте предпочтение NOT EXISTS или сначала отфильтруйте значения NULL в подзапросе.

-- Risky: if blocked_ids contains a NULL, this returns nothing
SELECT * FROM users
WHERE id NOT IN (SELECT user_id FROM blocked);

-- Safer
SELECT * FROM users
WHERE id NOT IN (SELECT user_id FROM blocked WHERE user_id IS NOT NULL);

IS DISTINCT FROM

PostgreSQL предоставляет операторы IS DISTINCT FROM и IS NOT DISTINCT FROM — операторы сравнения, безопасные для NULL.

В отличие от =, они считают два значения NULL равными, а NULL и обычное значение — различными, всегда возвращая true или false, но никогда не возвращая unknown.

SELECT
  NULL IS NOT DISTINCT FROM NULL AS a, -- true: both NULL = same
  NULL IS DISTINCT FROM 5        AS b, -- true: NULL differs from 5
  5 IS DISTINCT FROM 5          AS c; -- false: same value

Сравнение двух столбцов, допускающих NULL

При сравнении двух столбцов, значения которых могут быть NULL, обычный = не учитывает случай, когда оба значения равны NULL. IS NOT DISTINCT FROM корректно обрабатывает и этот случай.

Это особенно удобно для поиска строк, которые не изменились, даже если значение неизвестно.

-- Rows where old and new phone are 'the same',
-- counting NULL = NULL as same
SELECT id
FROM customer_changes
WHERE old_phone IS NOT DISTINCT FROM new_phone;

Подсчёт значений NULL

Практическое применение IS NULL — проверка качества данных: подсчёт количества строк, в которых отсутствует значение.

Объедините его с FILTER (PostgreSQL) или используйте CASE внутри COUNT, чтобы подсчитать значения NULL и не-NULL рядом друг с другом.

SELECT
  count(*) AS total,
  count(*) FILTER (WHERE phone IS NULL)     AS missing,
  count(*) FILTER (WHERE phone IS NOT NULL) AS present
FROM customers;

Проверки NULL в ограничениях CHECK

Проверки NULL можно использовать внутри ограничений CHECK, чтобы задавать правила вроде «если строка отправлена, у неё должна быть дата отправки».

Обратите внимание: ограничение CHECK считается выполненным, когда его условие равно true или unknown, поэтому внимательно учитывайте случаи с NULL.

CREATE TABLE orders (
  id        integer PRIMARY KEY,
  status    text NOT NULL,
  ship_date date,
  CHECK (status <> 'shipped' OR ship_date IS NOT NULL)
);

Рекомендации

Следуйте этим правилам, чтобы безопасно работать со значениями NULL:

  • Всегда проверяйте значения с помощью IS NULL / IS NOT NULL, никогда не используйте = NULL.
  • Остерегайтесь NOT IN в подзапросах, возвращающих допускающие NULL значения.
  • Используйте IS DISTINCT FROM для сравнения на равенство с безопасной обработкой NULL.
  • Проверяйте отсутствующие данные с помощью count(*) FILTER (...).
-- The reliable toolkit
WHERE col IS NULL
WHERE col IS NOT NULL
WHERE a IS DISTINCT FROM b
WHERE a IS NOT DISTINCT FROM b

Быстрая проверка

Вам нужны все клиенты, у которых в столбце phone нет значения. Какое предложение WHERE написано правильно?

Итоги

Вы узнали, как правильно проверять отсутствие значений с помощью IS NULL и IS NOT NULL, а также почему = NULL никогда не работает.

Вы также познакомились с ловушкой NOT IN, оператором IS DISTINCT FROM, безопасным при NULL, и способом проверять NULL с помощью FILTER. Далее вы узнаете, как заменять NULL разумными значениями по умолчанию с помощью COALESCE и NULLIF.

SELECT name FROM customers WHERE phone IS NULL;
SELECT name FROM customers WHERE phone IS NOT NULL;

Часто задаваемые вопросы

Урок «IS NULL и IS NOT NULL» бесплатный?

Да — полный текст урока «IS NULL и IS NOT NULL» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс SQL Academy, подпишись на CoddyKit PRO. Курс SQL Academy содержит 4 уроков всего.

Чему я научусь в уроке «IS NULL и IS NOT NULL»?

Правильно проверяйте отсутствующие значения Ты практикуешь SQL Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.

Нужен ли мне опыт, чтобы начать SQL Academy?

Предыдущий опыт не требуется. SQL Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 2 из 4.

Сколько времени занимает урок «IS NULL и IS NOT NULL»?

Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.

Можно ли писать и запускать код в этом уроке SQL Academy?

Да. Каждый урок SQL Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.

Все уроки этого курса

  1. Что на самом деле означает NULL
  2. IS NULL и IS NOT NULL
  3. COALESCE и NULLIF
  4. NULL в агрегатах и объединениях
← Назад к SQL Academy