К статье
Практический материал

Разработка и Конфигурация · 9 мин

Как получить тип значения в 1С

Как получить тип значения в 1С: функции ТипЗначения, ТипЗнч, Тип(), сравнение типов, проверка составного типа и типичные ошибки. Примеры кода на встроенном языке.

При разработке и доработке конфигураций 1С часто требуется узнать, какой тип имеет конкретное значение — например, чтобы проверить, пришла ли в параметр ссылка на документ, число или строка. От этого зависит логика обработки: какие свойства доступны, можно ли выполнять арифметические операции и как сравнивать значения.

Во встроенном языке 1С для этого есть три основных инструмента: функция ТипЗначения(), оператор ТипЗнч() и функция Тип(). Они решают похожие, но разные задачи, и путаница между ними — частая причина ошибок в коде.

Что такое тип значения в 1С

Каждое значение во встроенном языке 1С имеет тип: примитивный (Число, Строка, Дата, Булево, Неопределено, Null) или ссылочный (ДокументСсылка, СправочникСсылка и другие объектные типы конфигурации). Тип определяет набор доступных свойств, методов и допустимых операций.

Тип сам по себе представлен специальным объектом — Тип. Его нельзя сравнивать со строкой напрямую: выражение вида ТипЗнч(Значение) = "Строка" всегда вернёт Ложь, потому что сравнивается объект «Тип» со строковым литералом. Правильное сравнение выполняется через функцию Тип(), которая возвращает объект типа по его имени.

Функция ТипЗнч — основной способ получить тип

Оператор ТипЗнч(Значение) принимает любое значение и возвращает объект типа «Тип». Это универсальный способ, работающий и в тонком, и в толстом клиенте, и на сервере.

Значение = 42;

ТекущийТип = ТипЗнч(Значение);

// ТекущийТип — объект Тип «Число»

Сообщить(ТипЗнч(ТекущийТип)); // выведет: Тип

Обратите внимание на последнюю строку: если применить ТипЗнч() к уже полученному типу, результатом будет тип «Тип». Это полезно при отладке, когда нужно убедиться, что переменная содержит именно объект типа, а не значение данных.

Для анализа ссылочных значений ТипЗнч() возвращает конкретный тип ссылки, например «ДокументСсылка.РеализацияТоваровУслуг». Получить строковое имя типа можно через приведение к строке: Строка(ТипЗнч(Значение)) или через метаданные.

bsl
Если ТипЗнч(Параметр) = Тип("Число") Тогда
    Сумма = Сумма + Параметр;
ИначеЕсли ТипЗнч(Параметр) = Тип("Строка") Тогда
    Сообщить("Получена строка: " + Параметр);
КонецЕсли;

Функция Тип() — получение типа по имени

Функция Тип("ИмяТипа") создаёт объект типа по строковому имени. Именно она нужна для сравнения: ТипЗнч(Значение) = Тип("Дата"). Имя указывается так, как оно задано в конфигурации: "Число", "Строка", "СправочникСсылка.Номенклатура", "ДокументСсылка.ЗаказПокупателя".

Если указать несуществующее имя типа, будет вызвано исключение. Поэтому при работе с именами, которые могут отсутствовать в конфигурации (например, документ из необязательной подсистемы), вызов Тип() стоит оборачивать в попытку или предварительно проверять наличие объекта метаданных через Метаданные.НайтиПоПолномуИмени().

Попытка

НужныйТип = Тип("ДокументСсылка.ВнутреннееПотребление");

Исключение

НужныйТип = Неопределено;

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

ТипЗначения и где она применяется

Функция ТипЗначения() встречается в языке выражений компоновки данных и в ряде контекстов, где вычисляются выражения СКД, — например, в пользовательских полях отчётов. Там она возвращает тип выражения и используется вместе с функцией Тип() для условной логики в вычисляемых полях.

Во встроенном языке модулей аналогичную роль выполняет ТипЗнч(). Если вы видите ТипЗначения в чужом коде обычного модуля, скорее всего, это либо пользовательская функция, либо ошибка переноса выражения из поля СКД в модуль. Проверить просто: попробуйте скомпилировать модуль — синтакс-помощник и проверка конфигурации покажут, существует ли такой метод в данном контексте.

Сравнение типов и проверка составного типа

Простое сравнение ТипЗнч(А) = ТипЗнч(Б) проверяет идентичность типов двух значений. Но у реквизитов и параметров тип может быть составным — например, «Строка или Число». В этом случае удобнее работать с объектом ОписаниеТипов, который хранит список допустимых типов.

Метод СодержитТип() объекта ОписаниеТипов проверяет, входит ли конкретный тип в составной тип. Это правильный способ, когда нужно понять, можно ли записать значение в реквизит, не вызывая ошибку преобразования.

ОписаниеРеквизита = Метаданные.Документы.ЗаказПокупателя.Реквизиты.Комментарий.Тип;

Если ОписаниеРеквизита.СодержитТип(ТипЗнч(НовоеЗначение)) Тогда

// тип допустим, можно присваивать

КонецЕсли;

Проверка на примитивные типы и Неопределено

Значение Неопределено имеет собственный тип, который тоже определяется через ТипЗнч(Неопределено). Однако чаще проверку делают прямым сравнением: Если Значение = Неопределено Тогда. Для Null (значение из запроса при левом соединении) применяется аналогичное сравнение с Null.

Проверка «это ссылка или объект»

Типы «СправочникСсылка.Номенклатура» и «СправочникОбъект.Номенклатура» — разные типы. Если процедура должна принимать только ссылки, проверяйте точный тип. Универсальный способ определить, является ли значение ссылкой любого вида — проверка через ОбщегоНазначения.ЭтоСсылка() в типовых конфигурациях или анализ имени типа по метаданным.

Типичные ошибки
01
Сравнение ТипЗнч(Значение) со строкой вроде "Число" — всегда Ложь, нужна функция Тип("Число")
02
Вызов Тип("Имя") без проверки существования типа — исключение в подсистемах с необязательными объектами
03
Путаница между ТипЗнч в модуле и ТипЗначения в СКД — код не компилируется или работает не так
04
Сравнение типов ссылки и объекта одного вида как равных — это разные типы

Как узнать тип значения в отладчике и без кода

Не всегда нужно писать код. В конфигураторе при отладке достаточно остановиться на точке останова и посмотреть значение переменной в табло: тип отображается рядом со значением. Через «Вычислить выражение» (Shift+F9) можно выполнить ТипЗнч(Переменная) прямо в процессе отладки.

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

Контрольные точки

Как проверить результат

Сравнение типа в условии
Норма

Условие срабатывает на ожидаемых значениях

Тревожный признак

Условие никогда не выполняется — вероятно, сравнение со строкой вместо Тип()

Вывод типа через Сообщить
Норма

Выводится имя вида «Число» или «ДокументСсылка.ЗаказПокупателя»

Тревожный признак

Выводится «Тип» — вы применили ТипЗнч к типу, а не к значению

Тип из имени строкой
Норма

Тип() возвращает объект без исключения

Тревожный признак

Исключение — тип с таким именем отсутствует в конфигурации

Практический порядок действий

Когда нужно определить тип значения в рабочем коде, действуйте последовательно: сначала получите тип через ТипЗнч(), затем сравните его с нужным через Тип(), а для составных типов используйте ОписаниеТипов.СодержитТип(). Для разовой диагностики достаточно отладчика.

Порядок действий
  1. 1
    Получите тип: ТекущийТип = ТипЗнч(Значение)
  2. 2
    Сравните с нужным: ТекущийТип = Тип("Строка")
  3. 3
    Для составного типа используйте ОписаниеТипов.СодержитТип(ТекущийТип)
  4. 4
    Проверьте поведение в отладчике на реальных данных
  5. 5
    Для необязательных типов оберните Тип() в Попытку/Исключение
Итог

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

Тип значения получают через ТипЗнч(Значение), сравнивают с Тип("ИмяТипа"), для составных типов применяют ОписаниеТипов.СодержитТип(). ТипЗначения() — функция языка СКД, в модулях используется ТипЗнч. Никогда не сравнивайте тип со строкой напрямую.

Частые вопросы

Чем ТипЗнч отличается от ТипЗначения?

ТипЗнч() — функция встроенного языка модулей 1С, возвращает тип любого значения. ТипЗначения() — функция языка выражений системы компоновки данных, применяется в вычисляемых полях отчётов и настроек СКД. В программном коде модулей используется только ТипЗнч.

Почему сравнение ТипЗнч(Значение) = "Число" не работает?

ТипЗнч() возвращает объект типа «Тип», а не строку. Сравнение объекта со строкой всегда даёт Ложь. Правильно: ТипЗнч(Значение) = Тип("Число") — функция Тип() создаёт объект типа по имени.

Как получить имя типа строкой?

Используйте приведение к строке: Строка(ТипЗнч(Значение)). Для ссылочных значений ещё один способ — через метаданные: Значение.Метаданные().ПолноеИмя(), который вернёт, например, "Документ.РеализацияТоваровУслуг".

Как проверить, что значение — ссылка на любой справочник?

Точного универсального оператора нет. В типовых конфигурациях есть функция ОбщегоНазначения.ЭтоСсылка(). Альтернатива — получить метаданные значения через Метаданные.НайтиПоТипу(ТипЗнч(Значение)) и проверить, что объект принадлежит классу справочников.

Что вернёт ТипЗнч для Неопределено и Null?

Для Неопределено — тип «Неопределено», для Null — тип «Null». Обычно вместо анализа типа эти значения проверяют прямым сравнением: Если Значение = Неопределено или Если Значение = Null, что читается проще и работает быстрее.

Можно ли получить тип значения в запросе 1С?

Да, в языке запросов есть функция ТИПЗНАЧЕНИЯ(Поле) и оператор сравнения ССЫЛКА ... ТИП(...). Например: ГДЕ ТИПЗНАЧЕНИЯ(Регистратор) = ТИП(Документ.РеализацияТоваровУслуг). Это позволяет фильтровать записи по типу регистратора или составного поля прямо в запросе.