Проверить, заполнен ли параметр в 1С:Предприятие — одна из самых частых задач при разработке конфигураций, написании отчётов или обработок. Казалось бы, что может быть проще? Но даже опытные программисты иногда путаются в нюансах: когда использовать ПУСТОЕЗНАЧЕНИЕ(), а когда ЗНАЧЕНИЕЗАПОЛНЕНО(), как обрабатывать NULL в запросах или почему логическое выражение срабатывает не так, как ожидалось.

В этой статье разберём все способы проверки заполненности в 1С 8.3 и 1С 8.2, включая редкие случаи, когда стандартные функции ведут себя неочевидно. Вы узнаете, как избежать типичных ошибок при работе с реквизитами, параметрами запросов, динамическими списками и даже внешними источниками данных. А в конце — практические примеры кода, которые можно сразу использовать в своих проектах.

Особое внимание уделим разнице между "пустым" и "незаполненным" — эти понятия в не всегда совпадают. Например, строка с пробелом технически не пустая, но с точки зрения бизнес-логики может считаться незаполненной. Или параметр запроса, который возвращает NULL — как его правильно обработать, чтобы не получить ошибку при сравнении?

Если вы когда-нибудь сталкивались с тем, что условие ЕСЛИ Параметр = "" ТОГДА не срабатывает для пустой строки, или почему ЗНАЧЕНИЕЗАПОЛНЕНО(НЕОПРЕДЕЛЁНО) возвращает ИСТИНА — эта статья для вас.

1. Базовые функции: ПУСТОЕЗНАЧЕНИЕ vs ЗНАЧЕНИЕЗАПОЛНЕНО

Начнём с двух ключевых функций, которые чаще всего используются для проверки заполненности: ПУСТОЕЗНАЧЕНИЕ() и ЗНАЧЕНИЕЗАПОЛНЕНО(). На первый взгляд они кажутся взаимозаменяемыми, но на практике их поведение различается в зависимости от типа данных и контекста использования.

Функция ПУСТОЕЗНАЧЕНИЕ(Значение) возвращает ИСТИНА, если переданное значение считается "пустым" в . Что именно считается пустым?

  • 🔹 НЕОПРЕДЕЛЁНО — неинициализированная переменная
  • 🔹 NULL — значение из запроса или внешней БД
  • 🔹 Пустая строка ("")
  • 🔹 Пустая дата ('00010101')
  • 🔹 Пустой массив, структура, соответствие
  • 🔹 0 для числового типа (но только если явно не указано иное!)

Пример использования:

Если ПУСТОЕЗНАЧЕНИЕ(Параметр) Тогда

Сообщить("Параметр не заполнен!");

КонецЕсли;

Функция ЗНАЧЕНИЕЗАПОЛНЕНО(Значение) — это логическая противоположность ПУСТОЕЗНАЧЕНИЕ(). Она возвращает ИСТИНА, если значение не пустое. Однако здесь есть важный нюанс: ЗНАЧЕНИЕЗАПОЛНЕНО() работает корректно только с примитивными типами (строка, число, дата). Для объектных типов (справочники, документы) она может вести себя неожиданно.

💡

Если вам нужно проверить заполненность ссылочного типа (например, справочник или документ), лучше использовать конструкцию Значение <> НЕОПРЕДЕЛЁНО И Значение.Пустая() = ЛОЖЬ. Это надёжнее, чем ЗНАЧЕНИЕЗАПОЛНЕНО() для объектов.

Сравним поведение функций на примере:

Перем НовыйДокумент;

НовыйДокумент = Документы.ПоступлениеТоваров.СоздатьДокумент();

// ПУСТОЕЗНАЧЕНИЕ вернёт ЛОЖЬ (объект создан, но не записан)

Сообщить(ПУСТОЕЗНАЧЕНИЕ(НовыйДокумент)); // ЛОЖЬ

// ЗНАЧЕНИЕЗАПОЛНЕНО вернёт ИСТИНА (объект существует)

Сообщить(ЗНАЧЕНИЕЗАПОЛНЕНО(НовыйДокумент)); // ИСТИНА

// Но если документ не записан, он "пустой" с точки зрения бизнес-логики!

Сообщить(НовыйДокумент.Пустая()); // ИСТИНА

2. Особенности работы с NULL в запросах

Если вы работаете с результатами запросов или внешними источниками данных (например, SQL-базами), то вероятно столкнётесь с значением NULL. В оно обрабатывается иначе, чем "пустое" значение в прикладном коде.

Основные правила:

  • 🔹 NULL не равно НЕОПРЕДЕЛЁНО и не равно пустой строке. Сравнение Параметр = NULL всегда возвращает ЛОЖЬ!
  • 🔹 Для проверки на NULL используйте функцию ЕСТЬNULL(Значение, Замена) или конструкцию Значение ЕСТЬ NULL.
  • 🔹 В результатах запроса NULL преобразуется в НЕОПРЕДЕЛЁНО, но только если не используется ВЫБРАТЬ РАЗРЕШЕННЫЕ.

Пример обработки NULL в запросе:

Запрос = Новый Запрос;

Запрос.Текст =

"ВЫБРАТЬ

| Товары.Наименование КАК Наименование,

| ЕСТЬNULL(Товары.Артикул, """") КАК Артикул

|ИЗ

| Справочник.Товары КАК Товары";

Результат = Запрос.Выполнить();

Выборка = Результат.Выбрать();

Пока Выборка.Следующий() Цикл

// Артикул будет пустой строкой, если в базе NULL

Сообщить(Выборка.Артикул);

КонецЦикла;

Важно: если в запросе используется ЛЕВОЕ СОЕДИНЕНИЕ или ПОЛНОЕ СОЕДИНЕНИЕ, незаполненные поля автоматически получают значение NULL. Их нужно явным образом заменять на пустые строки или другие значения по умолчанию.

📊 Какой способ проверки NULL вы используете чаще?
ЕСТЬNULL в запросе
Значение ЕСТЬ NULL
ПУСТОЕЗНАЧЕНИЕ после выборки
Другой вариант

3. Проверка заполненности строк, чисел и дат

Для примитивных типов (строка, число, дата) проверка заполненности имеет свои нюансы. Рассмотрим их подробно.

Строки:

  • 🔹 Пустая строка ("") считается незаполненной.
  • 🔹 Строка с пробелами (" ") — заполненная! Чтобы игнорировать пробелы, используйте СОКРЛП(Строка) = "".
  • 🔹 НЕОПРЕДЕЛЁНО и NULL также считаются незаполненными.

Пример:

Функция СтрокаЗаполнена(Значение)

Возврат НЕ ПУСТОЕЗНАЧЕНИЕ(Значение) И СОКРЛП(Значение) <> "";

КонецФункции;

Числа:

  • 🔹 0заполненное значение! Если вам нужно игнорировать ноль, добавьте явную проверку: Значение <> 0.
  • 🔹 НЕОПРЕДЕЛЁНО и NULL — незаполненные.

Дата:

  • 🔹 Пустая дата ('00010101') считается незаполненной.
  • 🔹 Текущая дата (ТЕКУЩАЯДАТА()) — заполненная, даже если равна '00010101' (такое бывает при ошибках в данных).

Таблица сравнения поведения функций для разных типов:

Тип данных ПУСТОЕЗНАЧЕНИЕ() ЗНАЧЕНИЕЗАПОЛНЕНО() Примечание
Строка "" ИСТИНА ЛОЖЬ Пустая строка = незаполненная
Строка " " ЛОЖЬ ИСТИНА Пробелы — это символы!
Число 0 ЛОЖЬ ИСТИНА Ноль — это значение!
Дата '00010101' ИСТИНА ЛОЖЬ Пустая дата = незаполненная
НЕОПРЕДЕЛЁНО ИСТИНА ЛОЖЬ Неинициализированная переменная

4. Проверка ссылочных типов: справочники, документы, перечисления

Со ссылочными типами (справочники, документы, планы видов характеристик) ситуация сложнее. Здесь недостаточно проверить ПУСТОЕЗНАЧЕНИЕ() — нужно учитывать, что объект может быть:

  • 🔹 Неопределён (НЕОПРЕДЕЛЁНО)
  • 🔹 Пустой ссылкой (например, Справочники.Номенклатура.ПустаяСсылка())
  • 🔹 Существующей ссылкой, но с незаполненными реквизитами

Правильный способ проверки:

Если НЕ Значение ЕСТЬ НЕОПРЕДЕЛЁНО И НЕ Значение.Пустая() Тогда

// Объект заполнен и существует

КонецЕсли;

Для перечислений действуют те же правила, но есть нюанс: если перечисление не имеет значения по умолчанию, его проверка может вернуть НЕОПРЕДЕЛЁНО, даже если поле визуально "пустое" в форме.

⚠️ Внимание: При работе с динамическими списками или управляемыми формами не используйте ЗНАЧЕНИЕЗАПОЛНЕНО() для ссылочных типов. Эта функция не учитывает, что объект может быть пустой ссылкой, но не НЕОПРЕДЕЛЁНО. Например, после очистки поля в форме оно станет пустой ссылкой, а не НЕОПРЕДЕЛЁНО.

Пример обработки справочника в форме:

Процедура КонтрагентПриИзменении(Элемент)

Если Элемент.Значение.Пустая() Тогда

Сообщить("Контрагент не выбран!");

Иначе

Сообщить("Выбран: " + Элемент.Значение.Наименование);

КонецЕсли;

КонецПроцедуры;

5. Альтернативные способы проверки: ТИПЗНАЧЕНИЯ, ПОПЫТКА

Иногда стандартные функции не подходят, и приходится использовать обходные пути. Рассмотрим два полезных приёма.

1. Функция ТИПЗНАЧЕНИЯ()

Позволяет проверить, относится ли значение к определённому типу, не вызывая ошибку. Полезно, если параметр может быть разного типа (например, строка или число).

Пример:

Если ТИПЗНАЧЕНИЯ(Параметр) = Тип("Строка") Тогда

// Обработка строки

ИначеЕсли ТИПЗНАЧЕНИЯ(Параметр) = Тип("Число") Тогда

// Обработка числа

КонецЕсли;

2. Конструкция ПОПЫТКА...ИСКЛЮЧЕНИЕ

Используется, если при обращении к свойству незаполненного объекта может возникнуть ошибка. Например, при попытке получить Наименование у пустой ссылки.

Пример:

Попытка

ИмяКонтрагента = Контрагент.Наименование;

Исключение

ИмяКонтрагента = "Не указано";

КонецПопытки;

⚠️ Внимание: Конструкция ПОПЫТКА работает медленнее, чем прямая проверка. Используйте её только в случаях, когда другие способы не подходят (например, при работе с внешними COM-объектами или нестабильными источниками данных).
Когда ещё может пригодиться ПОПЫТКА?

При обращении к свойствам объектов, которые могут быть удалены или изменены в новой версии платформы. Например, если вы пишете универсальный код для разных конфигураций, где не все реквизиты гарантированно существуют.

6. Практические примеры для типовых задач

Рассмотрим реальные сценарии, где проверка заполненности параметров критична.

Пример 1: Проверка параметров отчёта

Допустим, у вас есть отчёт с optional-параметрами. Нужно вывести данные только по тем параметрам, которые заполнил пользователь.

Процедура СформироватьОтчёт(ДатаНачала, ДатаКонца, Контрагент = НЕОПРЕДЕЛЁНО)

Запрос = Новый Запрос;

Запрос.Текст =

"ВЫБРАТЬ

| Документ.Дата,

| Документ.Сумма

|ИЗ

| Документ.РеализацияТоваров КАК Документ

|ГДЕ

| Документ.Дата МЕЖДУ &ДатаНачала И &ДатаКонца";

Если ЗНАЧЕНИЕЗАПОЛНЕНО(Контрагент) Тогда

Запрос.Текст = Запрос.Текст + "

| И Документ.Контрагент = &Контрагент";

КонецЕсли;

Запрос.УстановитьПараметр("ДатаНачала", ДатаНачала);

Запрос.УстановитьПараметр("ДатаКонца", ДатаКонца);

Если ЗНАЧЕНИЕЗАПОЛНЕНО(Контрагент) Тогда

Запрос.УстановитьПараметр("Контрагент", Контрагент);

КонецЕсли;

Результат = Запрос.Выполнить();

КонецПроцедуры;

Пример 2: Обработка данных из внешнего источника (JSON, XML, REST)

При импорте данных из JSON или XML поля могут приходить как NULL, пустые строки или отсутствовать вовсе. Универсальный обработчик:

Функция ПолучитьЗначениеИзJSON(ОбъектJSON, ИмяПоля, ЗначениеПоУмолчанию = НЕОПРЕДЕЛЁНО)

Если НЕ ОбъектJSON.Свойство(ИмяПоля) Тогда

Возврат ЗначениеПоУмолчанию;

КонецЕсли;

Значение = ОбъектJSON[ИмяПоля];

Если ПУСТОЕЗНАЧЕНИЕ(Значение) Тогда

Возврат ЗначениеПоУмолчанию;

Иначе

Возврат Значение;

КонецЕсли;

КонецФункции;

Пример 3: Валидация данных перед записью документа

Перед записью документа нужно убедиться, что все обязательные реквизиты заполнены. Используем ПУСТОЕЗНАЧЕНИЕ() и Пустая():

Процедура ПередЗаписью(Отказ)

Если ПУСТОЕЗНАЧЕНИЕ(Объект.Контрагент) Или Объект.Контрагент.Пустая() Тогда

Сообщить("Укажите контрагента!", СтатусСообщения.Важное);

Отказ = Истина;

КонецЕсли;

Если ПУСТОЕЗНАЧЕНИЕ(Объект.Дата) Или Объект.Дата = '00010101' Тогда

Сообщить("Укажите дату документа!", СтатусСообщения.Важное);

Отказ = Истина;

КонецЕсли;

КонецПроцедуры;

Убедиться, что все обязательные реквизиты не равны НЕОПРЕДЕЛЁНО

Проверить ссылочные типы на Пустая()

Заменить NULL из запросов на значения по умолчанию

Обработать строки с пробелами (при необходимости)

Вывести пользователю конкретное сообщение об ошибке-->

7. Частые ошибки и как их избежать

Даже опытные разработчики иногда допускают ошибки при проверке заполненности. Вот самые распространённые из них:

Ошибка 1: Использование Значение = "" для проверки строк

Проблема: если строка содержит пробелы, сравнение не сработает. Правильно:

Если СОКРЛП(Значение) = "" Тогда...

Ошибка 2: Проверка чисел на ПУСТОЕЗНАЧЕНИЕ() без учёта нуля

Проблема: 0 — это заполненное значение. Если вам нужно игнорировать ноль:

Если ПУСТОЕЗНАЧЕНИЕ(Значение) ИЛИ Значение = 0 Тогда...

Ошибка 3: Прямое сравнение с NULL

Проблема: выражение Параметр = NULL всегда возвращает ЛОЖЬ. Правильно:

Если Параметр ЕСТЬ NULL Тогда...

Ошибка 4: Пропуск проверки на НЕОПРЕДЕЛЁНО для ссылочных типов

Проблема: пустая ссылка — это не то же самое, что НЕОПРЕДЕЛЁНО. Всегда проверяйте оба условия:

Если Значение = НЕОПРЕДЕЛЁНО ИЛИ Значение.Пустая() Тогда...

Ошибка 5: Игнорирование регистра в строках

Проблема: если пользователь ввёл данные в другом регистре, сравнение может не сработать. Используйте СТРНАЙТИ() или приведите к одному регистру:

Если НРЕГ(Значение) = НРЕГ("ИскомоеЗначение") Тогда...

⚠️ Внимание: В новых версиях платформы 1С:Предприятие (начиная с 8.3.20) появились дополнительные методы для работы с NULL в запросах, например ВЫРАЗИТЬ(Поле КАК Строка). Если вы поддерживаете старые версии, учитывайте это при написании универсального кода.

8. Оптимизация кода: когда и что использовать

Выбор между ПУСТОЕЗНАЧЕНИЕ(), ЗНАЧЕНИЕЗАПОЛНЕНО() и другими методами зависит от контекста. Вот рекомендации по оптимизации:

1. Для примитивных типов (строка, число, дата):

  • 🔹 Используйте ПУСТОЕЗНАЧЕНИЕ() для универсальной проверки.
  • 🔹 Для строк с пробелами добавляйте СОКРЛП().
  • 🔹 Для чисел явно проверяйте ноль, если он считается "пустым".

2. Для ссылочных типов:

  • 🔹 Всегда проверяйте НЕОПРЕДЕЛЁНО и Пустая().
  • 🔹 Избегайте ЗНАЧЕНИЕЗАПОЛНЕНО() — она не надёжна для объектов.

3. В запросах:

  • 🔹 Заменяйте NULL на значения по умолчанию с помощью ЕСТЬNULL().
  • 🔹 Для сравнения используйте Значение ЕСТЬ NULL.

4. Для внешних данных (JSON, XML):

  • 🔹 Проверяйте существование поля перед доступом к нему.
  • 🔹 Используйте ПОПЫТКА, если структура данных нестабильна.

Сводная таблица рекомендаций:

Контекст Рекомендуемый метод Пример
Примитивные типы (строка, число) ПУСТОЕЗНАЧЕНИЕ() Если ПУСТОЕЗНАЧЕНИЕ(Строка) Тогда...
Ссылочные типы (справочники, документы) Значение = НЕОПРЕДЕЛЁНО ИЛИ Значение.Пустая() Если Контрагент = НЕОПРЕДЕЛЁНО Или Контрагент.Пустая() Тогда...
Запросы с NULL ЕСТЬNULL() или Значение ЕСТЬ NULL ЕСТЬNULL(Поле, 0) КАК ПолеБезNULL
Внешние данные (JSON, XML) Проверка свойства + ПУСТОЕЗНАЧЕНИЕ() Если НЕ Объект.Свойство("Поле") Или ПУСТОЕЗНАЧЕНИЕ(Объект.Поле) Тогда...
Динамические списки, формы Элемент.Значение.Пустая() Если ЭлементФормы.Значение.Пустая() Тогда...
💡

Для максимальной надёжности комбинируйте проверки. Например, для справочника: Если Контрагент <> НЕОПРЕДЕЛЁНО И НЕ Контрагент.Пустая() Тогда.... Это покрывает все случаи: неопределённость, пустую ссылку и реально заполненный объект.

FAQ: Ответы на частые вопросы

Почему ЗНАЧЕНИЕЗАПОЛНЕНО(НЕОПРЕДЕЛЁНО) возвращает ИСТИНА?

Это известная особенность функции ЗНАЧЕНИЕЗАПОЛНЕНО(). Она считает, что НЕОПРЕДЕЛЁНО — это "заполненное" значение (поскольку оно существует как объект). Чтобы избежать путаницы, используйте ПУСТОЕЗНАЧЕНИЕ() или явную проверку на НЕОПРЕДЕЛЁНО.

Как проверить, что массив не пустой?

Для массивов используйте Значение.Количество() > 0. Функция ПУСТОЕЗНАЧЕНИЕ() вернёт ИСТИНА только для неинициализированного массива (НЕОПРЕДЕЛЁНО), но не для пустого (Новый Массив). Пример:

Если Массив = НЕОПРЕДЕЛЁНО Или Массив.Количество() = 0 Тогда

// Массив пустой

КонецЕсли;

Можно ли использовать TRY...EXCEPT вместо ПОПЫТКА?

Нет, в нет конструкции TRY...EXCEPT (как в некоторых других языках). Единственный аналог — ПОПЫТКА...ИСКЛЮЧЕНИЕ. Он работает медленнее прямой проверки, поэтому используйте его только там, где другие методы не подходят.

Как проверить заполненность параметра в управляемой форме?

В управляемых формах значения элементов доступны через ЭлементыФормы.ИмяЭлемента.Значение. Для проверки используйте:

Если ЭлементыФормы.Контрагент.Значение.Пустая() Тогда

Сообщить("Выберите контрагента!");

КонецЕсли;

Для полей ввода (строка, число) подходит