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

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

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

Как определить тип значения в запросе 1С: функции ТИПЗНАЧЕНИЯ, ТИП, ССЫЛКА, ВЫРАЗИТЬ. Примеры кода, сравнение методов, типичные ошибки и ответы на вопросы.

В запросах 1С нередко требуется узнать, какого типа значение хранится в поле: это нужно при работе с составными типами, характеристиками, планами обмена и любыми реквизитами, где может лежать ссылка на разные объекты. Платформа предоставляет для этого несколько инструментов языка запросов — функции ТИПЗНАЧЕНИЯ, ТИП, оператор ССЫЛКА и конструкцию ВЫРАЗИТЬ.

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

Ниже разобраны все рабочие приёмы определения типа значения в запросе 1С с примерами кода, сравнением подходов, типичными ошибками и рекомендациями по проверке результата.

Функция ТИПЗНАЧЕНИЯ — основной способ получить тип поля

Функция ТИПЗНАЧЕНИЯ принимает поле запроса и возвращает его тип. Результат можно вывести как отдельное поле выборки или использовать в условии ГДЕ. Это универсальный инструмент, работающий и со ссылочными, и с примитивными типами.

// Вывести тип значения аналитики в результат запроса

ВЫБРАТЬ

Регистр.Аналитика КАК Значение,

ТИПЗНАЧЕНИЯ(Регистр.Аналитика) КАК ТипЗначения

ИЗ

РегистрСведений.АналитикаУчета КАК Регистр

Чаще функция применяется в условии отбора. Тип сравнивается с литералом, который задаётся через функцию ТИП с указанием конкретного объекта метаданных:

ВЫБРАТЬ

Регистр.Аналитика КАК Значение

ИЗ

РегистрСведений.АналитикаУчета КАК Регистр

ГДЕ

ТИПЗНАЧЕНИЯ(Регистр.Аналитика) = ТИП(Справочник.Номенклатура)

Важно понимать, что ТИПЗНАЧЕНИЯ вычисляется для каждой строки результата. На больших таблицах с составными типами это может заметно увеличить время выполнения запроса, особенно если условие не поддерживается индексом.

Функция ТИП — литерал для сравнения типов

Функция ТИП сама по себе не определяет тип значения — она формирует значение типа «Тип», с которым сравнивается результат ТИПЗНАЧЕНИЯ. Это две части одной конструкции: ТИПЗНАЧЕНИЯ извлекает тип из данных, ТИП задаёт эталон для сравнения.

Допустимые формы записи:

  • ТИП(Справочник.Номенклатура) — ссылочный тип справочника;
  • ТИП(Документ.ПоступлениеТоваровУслуг) — ссылочный тип документа;
  • ТИП(Перечисление.СтавкиНДС) — тип перечисления;
  • ТИП(Строка), ТИП(Число), ТИП(Дата), ТИП(Булево) — примитивные типы.

Проверку можно инвертировать через неравенство, например отобрать все строки, где аналитика заполнена, но не является номенклатурой:

ГДЕ

НЕ Регистр.Аналитика ЕСТЬ NULL

И ТИПЗНАЧЕНИЯ(Регистр.Аналитика) <> ТИП(Справочник.Номенклатура)

Обратите внимание: для пустых ссылок и NULL тип определяется по-разному. Пустая ссылка справочника имеет тип этого справочника, а NULL типа не имеет — поэтому проверку на NULL стоит выполнять отдельно и до сравнения типов.

Оператор ССЫЛКА — быстрая проверка ссылочных полей

Оператор ССЫЛКА проверяет, указывает ли поле на объект заданной таблицы. Синтаксически это выглядит как условие «Поле ССЫЛКА Справочник.Номенклатура» и возвращает истину или ложь. Для ссылочных типов это предпочтительный вариант: запрос читается проще, а СУБД в ряде случаев выполняет такую проверку эффективнее.

ВЫБРАТЬ

Хозрасчетный.Субконто1 КАК Аналитика

ИЗ

РегистрБухгалтерии.Хозрасчетный.Остатки(&Период, , , ) КАК Хозрасчетный

ГДЕ

Хозрасчетный.Субконто1 ССЫЛКА Справочник.Номенклатура

Ограничение оператора очевидно из названия: он работает только со ссылочными типами. Проверить, является ли значение строкой или числом, через ССЫЛКА нельзя — для примитивных типов используется только пара ТИПЗНАЧЕНИЯ + ТИП.

Сравнение способов определения типа

ТИПЗНАЧЕНИЯ + ТИП

Универсальный вариант: работает со ссылками и примитивами, позволяет вывести тип в результат. Медленнее на больших выборках.

Оператор ССЫЛКА

Только ссылочные типы. Короче и обычно эффективнее; нельзя вывести тип как поле результата.

ВЫРАЗИТЬ

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

Конструкция ВЫРАЗИТЬ — сужение составного типа

ВЫРАЗИТЬ не определяет тип, а приводит значение составного поля к указанному типу. Если фактическое значение не соответствует целевому типу, результатом будет NULL. Это позволяет одновременно «проверить» тип и получить доступ к реквизитам объекта через точку.

ВЫБРАТЬ

ВЫРАЗИТЬ(Регистр.Аналитика КАК Справочник.Номенклатура).Артикул КАК Артикул

ИЗ

РегистрСведений.АналитикаУчета КАК Регистр

ГДЕ

Регистр.Аналитика ССЫЛКА Справочник.Номенклатура

Типичный сценарий: поле имеет составной тип (несколько справочников и документов), а в отчёте нужно вывести реквизит, существующий только у одного из них. Сначала условие ССЫЛКА отсекает лишние строки, затем ВЫРАЗИТЬ открывает доступ к реквизиту.

Дополнительно ВЫРАЗИТЬ применяется для усечения строк и чисел: ВЫРАЗИТЬ(Поле КАК Строка(100)). Это важно при соединениях по строковым полям и при группировках — строки неограниченной длины в ряде операций недопустимы.

Порядок действий при работе с составным типом
  1. 1
    Определите, какие типы реально встречаются в поле — выведите ТИПЗНАЧЕНИЯ(Поле) с группировкой.
  2. 2
    Выберите способ проверки: ССЫЛКА для ссылок, ТИПЗНАЧЕНИЯ + ТИП для примитивов или вывода типа.
  3. 3
    Добавьте ВЫРАЗИТЬ, если нужны реквизиты конкретного объекта.
  4. 4
    Проверьте обработку NULL и пустых ссылок отдельными условиями.
  5. 5
    Выполните запрос на реальных данных и сверьте количество строк с ожидаемым.

Определение типа в СКД и динамических списках

В системе компоновки данных те же функции доступны в тексте запроса набора данных. Дополнительно тип можно использовать в отборах СКД: поле ТИПЗНАЧЕНИЯ(Поле) выводится как вычисляемое, и на него накладывается отбор в настройках отчёта. Это удобно, когда пользователь должен сам выбирать, по какому типу аналитики строить отчёт.

В динамических списках с произвольным запросом условия с ТИПЗНАЧЕНИЯ работают, но есть нюанс: если список должен поддерживать интерактивную сортировку и отборы, тяжёлые функции в секции ГДЕ могут конфликтовать с динамическим обновлением и ухудшать отзывчивость формы. По возможности такие проверки выносят во временные таблицы пакетного запроса.

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

Удобный приём диагностики составного поля — запрос с группировкой: ВЫБРАТЬ ТИПЗНАЧЕНИЯ(Поле) КАК Тип, КОЛИЧЕСТВО(*) КАК Количество ... СГРУППИРОВАТЬ ПО ТИПЗНАЧЕНИЯ(Поле). Он сразу показывает, какие типы реально хранятся в данных и в каком объёме.
ПЗ
Практическое замечание

Типичные ошибки и ограничения

Самая частая ошибка — попытка обратиться к реквизиту через точку от поля составного типа без ВЫРАЗИТЬ. Конструктор запросов такое поле даже не покажет в списке доступных, а при ручном наборе запрос не пройдёт проверку. Лечится приведением типа перед обращением к реквизиту.

Вторая группа ошибок связана с NULL. Если поле допускает NULL (например, после левого соединения), ТИПЗНАЧЕНИЯ вернёт NULL, и сравнение с ТИП(...) даст не ложь, а неопределённость — строка выпадет из результата. Поэтому условия на тип комбинируют с проверкой ЕСТЬ NULL.

Третья типичная проблема — производительность. Условие вида ТИПЗНАЧЕНИЯ(Поле) = ТИП(...) не использует индекс по полю, поэтому на больших таблицах фильтрация превращается в полное сканирование. Если запрос выполняется медленно, сначала отберите данные по другим индексированным условиям во временную таблицу, а проверку типа примените уже к ней.

Типичные ошибки
01
Обращение к реквизиту составного поля без ВЫРАЗИТЬ — запрос не проходит проверку или возвращает ошибку.
02
Игнорирование NULL: строки с NULL выпадают из результата при сравнении типов, хотя ожидалась ложь.
03
Сравнение ТИПЗНАЧЕНИЯ со строкой ('Справочник.Номенклатура') — тип нельзя сравнивать со строкой, нужен литерал ТИП().
04
Проверка примитивного типа через ССЫЛКА — оператор работает только со ссылками.
05
Проверка типа на полной таблице без предварительного отбора — запрос выполняется неприемлемо долго.

Проверка результата и контрольные точки

После написания запроса результат стоит проверить в консоли запросов на реальных данных. Ключевой критерий — количество строк: если после добавления условия на тип выборка стала пустой, хотя данные нужного типа точно есть, чаще всего причина в NULL, в неверно указанном имени объекта метаданных или в том, что поле хранит значение другого типа, чем ожидалось.

Полезно сравнить результат двух способов: один и тот же отбор через ССЫЛКА и через ТИПЗНАЧЕНИЯ для ссылочного поля обязан давать идентичный набор строк. Расхождение — признак ошибки в условиях или наличия в данных нестандартных значений.

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

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

Количество строк после отбора по типу
Норма

Совпадает с количеством по диагностическому запросу с группировкой по ТИПЗНАЧЕНИЯ

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

Ноль строк или меньше ожидаемого — проверяйте NULL и имя объекта в ТИП()

Результат ВЫРАЗИТЬ
Норма

Для строк нужного типа реквизит заполнен, для остальных NULL

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

NULL во всех строках — тип в ВЫРАЗИТЬ не совпадает с фактическим

Скорость выполнения
Норма

Запрос отрабатывает за приемлемое время на рабочей базе

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

Резкое замедление после добавления ТИПЗНАЧЕНИЯ — переносите проверку во временную таблицу

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

Как определить тип значения в запросе 1С?

Используйте функцию ТИПЗНАЧЕНИЯ(Поле) — она возвращает тип значения поля. Для сравнения применяйте литерал ТИП(Справочник.Номенклатура), а для ссылочных полей допустим более короткий оператор ССЫЛКА.

Чем ССЫЛКА отличается от ТИПЗНАЧЕНИЯ?

ССЫЛКА — логическая проверка «указывает ли поле на таблиц», работает только со ссылочными типами и обычно эффективнее. ТИПЗНАЧЕНИЯ возвращает сам тип, подходит для примитивов и позволяет вывести тип в результат запроса.

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

Через сравнение ТИПЗНАЧЕНИЯ(Поле) = ТИП(Строка) или ТИП(Число). Оператор ССЫЛКА для примитивных типов не применяется.

Почему условие с ТИПЗНАЧЕНИЯ отсекает строки с NULL?

Потому что у NULL нет типа: сравнение NULL с любым типом даёт неопределённость, и строка исключается из результата. Добавьте отдельную обработку через ЕСТЬ NULL или ЕСТЬNULL.

Можно ли получить тип значения без запроса, в коде?

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

Итог

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

Тип значения в запросе 1С определяют функцией ТИПЗНАЧЕНИЯ с литералом ТИП, для ссылок удобнее оператор ССЫЛКА, а доступ к реквизитам составного поля даёт ВЫРАЗИТЬ. Всегда учитывайте NULL и проверяйте влияние условий на скорость запроса.