Разработка и Конфигурация · 10 мин
Как в запросе 1С проверить поле на пустую строку
Как в запросе 1С проверить строковое поле на пустое значение: сравнение с пустой строкой, ПОДОБНО, NULL, длина строки. Примеры кода, ошибки и FAQ.
Проверка на пустую строку — одна из самых частых задач при написании запросов в 1С. На первый взгляд всё просто: сравнить поле с пустым литералом "". Но на практике разработчики сталкиваются с нюансами: значение может быть не пустой строкой, а NULL, неопределённым значением или строкой из пробелов, и каждый случай требует своего подхода.
В языке запросов 1С строка считается пустой, если её длина равна нулю. При этом пробелы, неразрывные пробелы и другие невидимые символы — это уже не пустая строка, а строка с содержимым. Это принципиальное отличие, которое часто становится причиной «неправильно работающих» запросов.
Дополнительная сложность возникает из-за левых соединений: когда соединение не находит пару, поля правой таблицы получают значение NULL, а не пустую строку. Простое сравнение ГДЕ Поле = "" такие записи не отберёт, потому что NULL не равен ничему, включая сам себя.
Базовая проверка: сравнение с пустым литералом
Самый прямой способ — сравнить строковое поле с пустой строкой в секции ГДЕ. Пустая строка в языке запросов записывается двумя двойными кавычками подряд.
ВЫБРАТЬ
Контрагенты.Ссылка,
Контрагенты.НаименованиеПолное
ИЗ
Справочник.Контрагенты КАК Контрагенты
ГДЕ
Контрагенты.НаименованиеПолное = ""
Такой запрос вернёт всех контрагентов, у которых реквизит «НаименованиеПолное» физически не заполнен. Обратное условие — отбор только заполненных значений — записывается через оператор неравенства:
ГДЕ
Контрагенты.НаименованиеПолное <> ""
Условие можно размещать не только в ГДЕ, но и в ИМЕЮЩИЕ, в условиях соединения ПО и в конструкциях ВЫБОР КОГДА ... ТОГДА. Логика сравнения везде одинаковая.
ГДЕ
ЕСТЬNULL(Таблица.СтроковоеПоле, "") = ""NULL вместо пустой строки: главный подводный камень
Когда поле попадает в результат запроса через левое соединение и для записи не нашлось пары, значение поля становится NULL. Сравнение NULL = "" возвращает не «истина» и не «ложь», а неопределённый результат, поэтому такая запись просто не попадёт в выборку ни при = "", ни при <> "".
Чтобы корректно обработать этот случай, используйте функцию ЕСТЬNULL(), которая заменяет NULL на указанное значение до сравнения:
ВЫБРАТЬ
Заказы.Номер,
ЕСТЬNULL(Контрагенты.НаименованиеПолное, "") КАК НаименованиеПолное
ИЗ
Документ.ЗаказПокупателя КАК Заказы
ЛЕВОЕ СОЕДИНЕНИЕ Справочник.Контрагенты КАК Контрагенты
ПО Заказы.Контрагент = Контрагенты.Ссылка
ГДЕ
ЕСТЬNULL(Контрагенты.НаименованиеПолное, "") = ""
Альтернатива — явная проверка на NULL через оператор ЕСТЬ NULL с логическим ИЛИ:
ГДЕ
Контрагенты.НаименованиеПолное = ""
ИЛИ Контрагенты.НаименованиеПолное ЕСТЬ NULL
Строка из пробелов: почему она не пустая
Частая ситуация: пользователь ввёл в поле несколько пробелов, визуально поле выглядит пустым, но запрос с условием = "" его не находит. Причина в том, что строка из пробелов имеет ненулевую длину и формально не является пустой.
Если нужно отобрать и такие значения, есть несколько подходов. Первый — проверка длины строки с предварительным удалением пробелов. Однако в языке запросов 1С нет функции сокращения пробелов, поэтому «чистого» способа сделать это внутри запроса нет. Второй подход — использовать оператор ПОДОБНО с шаблоном, который находит строки, состоящие только из пробелов, хотя составить универсальный шаблон для произвольного числа пробелов затруднительно.
Практичное решение — не бороться с пробелами в запросе, а чистить данные на этапе записи: обрабатывать значение через СокрЛП() в модуле объекта перед записью. Тогда в базе не появятся «псевдопустые» строки, и запросы останутся простыми.
Проверка через длину строки
В языке запросов есть функция ДЛИНАСТРОКИ() (в английском синтаксисе — LENGTH), которая возвращает число символов в строке. С её помощью проверка на пустоту выглядит так:
ГДЕ
ДЛИНАСТРОКИ(Контрагенты.НаименованиеПолное) = 0
По смыслу это эквивалентно сравнению с пустой строкой, и в большинстве случаев предпочтительнее именно сравнение с "" — оно читается проще. Однако ДЛИНАСТРОКИ() полезна, когда нужно отобрать не только пустые, но и «подозрительно короткие» значения, например наименования короче трёх символов при поиске некорректно заполненных элементов.
Учтите ограничение: функция ДЛИНАСТРОКИ() не применяется к полям неограниченной длины (строка без указания длины) и к полям типа «ХранилищеЗначения». Для таких полей остаётся только сравнение с литералом.
Неопределённая длина и составные типы
Если реквизит имеет составной тип, например «Строка или СправочникСсылка», сравнение Поле = "" вернёт истину только для пустой строки, но не для пустой ссылки. Для составных полей проверку нужно строить с учётом всех допустимых «пустых» значений каждого типа:
ГДЕ
Поле = ""
ИЛИ Поле = ЗНАЧЕНИЕ(Справочник.Контрагенты.ПустаяСсылка)
ИЛИ Поле = НЕОПРЕДЕЛЕНО
ИЛИ Поле ЕСТЬ NULL
Для полей неограниченной длины (тип «Строка» без указания длины) сравнение с "" работает, но такие поля нельзя использовать в группировках и соединениях без приведения типа. Если требуется сгруппировать или соединить по такому полю, приведите его через ВЫРАЗИТЬ(Поле КАК Строка(255)), понимая, что содержимое длиннее указанного размера будет усечено.
Сравнение вариантов проверки
Базовый вариант для обычных строковых реквизитов без соединений. Не ловит NULL и строки из пробелов.
Надёжный вариант для полей из левых соединений. Заменяет NULL пустой строкой до сравнения.
Альтернатива ЕСТЬNULL, явно показывает оба случая. Чуть длиннее, но нагляднее при сложных условиях.
Подходит, когда дополнительно нужно фильтровать по длине. Не работает со строками неограниченной длины.
Проверка результата и типичные ошибки
После написания запроса проверьте его на реальных данных, а не только на синтаксис. Откройте консоль запросов, выполните запрос без условия и посмотрите, какие фактически значения содержит поле: пустые строки, пробелы или NULL. Затем добавьте условие и убедитесь, что количество записей изменилось ожидаемо.
Контрольный приём: выполните запрос с условием = "" и с условием <> "" по очереди. Если сумма записей в обоих выборках меньше общего числа записей в таблице, значит, часть данных содержит NULL и теряется при обоих сравнениях — нужен ЕСТЬNULL().
Проверка параметра запроса из кода
Отдельный сценарий — когда пустая строка передаётся в запрос как параметр, и по ней нужно либо отфильтровать данные, либо отключить фильтр. Стандартный приём — условие с проверкой самого параметра:
ГДЕ
(&Комментарий = ""
ИЛИ Таблица.Комментарий = &Комментарий)
В коде перед установкой параметра полезно нормализовать значение через СокрЛП(), чтобы случайные пробелы не ломали логику:
Запрос.УстановитьПараметр("Комментарий", СокрЛП(Комментарий));
Если нужно проверить строковую переменную на пустоту во встроенном языке (не в запросе), используйте функцию ПустаяСтрока(Значение) — она возвращает истину и для пустой строки, и для строки, состоящей только из пробельных символов. Это удобнее, чем сравнение с "" после СокрЛП().
Как проверить результат
Суммы совпадают — NULL в данных нет
Сумма меньше — есть NULL, добавьте ЕСТЬNULL
Все пустые значения отобраны
Часть не отобрана — вероятно, это строки из пробелов
Выборка сформирована
Ошибка про ДЛИНАСТРОКИ — поле неограниченной длины
Частые вопросы
Чем отличается проверка в запросе от функции ПустаяСтрока() в коде?
В запросе доступно только сравнение с литералом "", которое не считает строку из пробелов пустой. Функция встроенного языка ПустаяСтрока() дополнительно считает пустыми строки, состоящие из пробелов, табуляций и переводов строк. Если нужна такая логика в запросе, чистите данные до записи или обрабатывайте результат в коде.
Почему запрос с условием Поле = "" не находит записи после левого соединения?
Потому что для несоединённых записей поле содержит NULL, а любое сравнение с NULL не даёт истины. Оберните поле в ЕСТЬNULL(Поле, "") или добавьте условие ИЛИ Поле ЕСТЬ NULL.
Можно ли проверить на пустую строку поле неограниченной длины?
Да, сравнение Поле = "" работает и для строк неограниченной длины. Не работает для таких полей функция ДЛИНАСТРОКИ(), а также их нельзя использовать в группировках и соединениях без приведения типа через ВЫРАЗИТЬ().
Как отобрать строки, состоящие только из пробелов?
Надёжного способа внутри запроса нет, так как в языке запросов отсутствует аналог СокрЛП(). Практические варианты: очищать значения через СокрЛП() при записи данных или выгрузить результат и отфильтровать в коде с помощью ПустаяСтрока().
Что быстрее: сравнение с "" или ДЛИНАСТРОКИ(Поле) = 0?
По смыслу оба варианта эквивалентны, и заметной разницы в производительности на типовых объёмах данных обычно нет. Предпочтительнее сравнение с "": оно проще читается и работает со строками неограниченной длины.
Как проверить составное поле, где может быть и строка, и ссылка?
Проверяйте все «пустые» значения допустимых типов через ИЛИ: пустую строку "", пустые ссылки через ЗНАЧЕНИЕ(Справочник.Имя.ПустаяСсылка), значение НЕОПРЕДЕЛЕНО и ЕСТЬ NULL, если поле участвует в соединениях.
Что важно запомнить
Базовая проверка — ГДЕ Поле = "". Для полей из соединений обязательно добавляйте ЕСТЬNULL или проверку ЕСТЬ NULL, иначе записи молча потеряются. Строки из пробелов пустыми не считаются — чистите их при записи данных через СокрЛП().