Разработка и Конфигурация · 9 мин
Как в 1С проверить, что колонка существует
Как в 1С проверить существование колонки таблицы значений: метод Найти, работа с коллекцией колонок, проверка в запросе и типовые ошибки разработчиков.
При разработке на платформе 1С:Предприятие часто возникает ситуация, когда структура таблицы значений заранее неизвестна: данные загружаются из файла, приходят из внешнего источника или формируются динамически. Обращение к несуществующей колонке вызывает ошибку «Поле объекта не обнаружено», которая прерывает выполнение кода. Чтобы этого избежать, перед обращением к колонке нужно проверить её наличие.
Основной инструмент для такой проверки — коллекция Колонки таблицы значений и её метод Найти(). Метод возвращает объект колонки, если она найдена, и Неопределено, если колонки с таким именем нет. Этого достаточно для большинства прикладных задач.
Отдельный случай — проверка наличия поля в результате запроса, в дереве значений, в строке табличной части или в структуре. У каждого объекта свои методы, и их важно не путать. Ниже разобраны рабочие приёмы с примерами кода, ограничениями и типичными ошибками.
Базовый способ: метод Найти у коллекции колонок
У любой таблицы значений есть свойство Колонки — это коллекция объектов типа «КолонкаТаблицыЗначений». У коллекции есть метод Найти(ИмяКолонки), который выполняет поиск по имени. Поиск нечувствителен к регистру: «Сумма», «СУММА» и «сумма» считаются одной и той же колонкой.
Типовой код проверки выглядит так:
Если ТаблицаДанных.Колонки.Найти("Сумма") = Неопределено Тогда
// Колонки нет — создаём её или пропускаем обработку
ТаблицаДанных.Колонки.Добавить("Сумма", Новый ОписаниеТипов("Число"));
Иначе
// Колонка существует, работаем с ней
ИтогСуммы = ТаблицаДанных.Итог("Сумма");
КонецЕсли;
Важно понимать, что метод возвращает не булево значение, а объект колонки или Неопределено. Поэтому сравнение пишут именно через = Неопределено или <> Неопределено. Попытка использовать результат напрямую в условии без сравнения приведёт к ошибке преобразования типов.
Через найденный объект колонки можно дополнительно узнать её тип, заголовок и ширину. Это полезно, когда недостаточно знать, что колонка есть, — нужно ещё убедиться, что она имеет подходящий тип данных.
Функция КолонкаСуществует(Таблица, ИмяКолонки)
Возврат Таблица.Колонки.Найти(ИмяКолонки) <> Неопределено;
КонецФункцииПроверка колонки в результате запроса и выборке
Когда данные получены запросом, структура полей определяется текстом запроса. У объекта «РезультатЗапроса» также есть коллекция Колонки, и проверка работает аналогично:
РезультатЗапроса = Запрос.Выполнить();
Если РезультатЗапроса.Колонки.Найти("Количество") <> Неопределено Тогда
// Поле есть в результате
КонецЕсли;
Такая проверка особенно актуальна, когда текст запроса собирается динамически или поля добавляются по условию. Если запрос статический и поле перечислено в списке выборки, отдельная проверка обычно не нужна — достаточно контроля на этапе разработки.
Таблица значений, полученная методом Выгрузить() из результата запроса, сохраняет состав колонок, поэтому к ней применим тот же метод Найти(). Учтите, что имена колонок при выгрузке совпадают с именами (псевдонимами) полей запроса.
Проверка в дереве значений и табличной части
Дерево значений по устройству похоже на таблицу значений и тоже имеет коллекцию Колонки. Проверка выполняется тем же методом Найти() без каких-либо отличий. Это удобно при обработке иерархических данных, загруженных из внешних источников.
С табличной частью объекта ситуация иная: у неё нет программно доступной коллекции колонок в том же виде. Состав реквизитов табличной части определяется метаданными. Проверить наличие реквизита можно через объект метаданных:
МетаданныеТЧ = ДокументОбъект.Метаданные().ТабличныеЧасти.Товары;
Если МетаданныеТЧ.Реквизиты.Найти("Характеристика") <> Неопределено Тогда
// Реквизит есть в конфигурации
КонецЕсли;
Такой подход нужен в универсальных обработках, которые должны работать с разными конфигурациями, где состав реквизитов может отличаться. В типовом коде, привязанном к конкретной конфигурации, проверка через метаданные обычно избыточна.
Универсальная функция проверки
Чтобы не дублировать код, проверку удобно оформить как функцию общего модуля. Она принимает таблицу и имя колонки и возвращает булево значение:
Функция ЕстьКолонка(ТаблицаИлиДерево, ИмяКолонки) Экспорт
Если ТаблицаИлиДерево = Неопределено Тогда
Возврат Ложь;
КонецЕсли;
Возврат ТаблицаИлиДерево.Колонки.Найти(ИмяКолонки) <> Неопределено;
КонецФункции
Функцию можно расширить проверкой типа колонки. Например, если дальнейший код ожидает числовую колонку, имеет смысл сразу убедиться, что тип значения содержит «Число»:
Колонка = Таблица.Колонки.Найти("Сумма");
Если Колонка <> Неопределено
И Колонка.ТипЗначения.СодержитТип(Тип("Число")) Тогда
// Можно выполнять арифметические операции
КонецЕсли;
- 1Определите, с каким объектом работаете: таблица значений, дерево значений, результат запроса или табличная часть
- 2Для таблицы, дерева или результата запроса вызовите Колонки.Найти("ИмяКолонки")
- 3Сравните результат с Неопределено
- 4Если колонки нет — добавьте её через Колонки.Добавить() либо пропустите обработку
- 5Проверьте тип колонки, если дальнейший код зависит от типа данных
Типичные ошибки и ограничения
Самая частая ошибка — обращение к колонке без проверки в цикле по строкам. Если колонка отсутствует, код падает на первой же итерации с ошибкой «Поле объекта не обнаружено». Проверку достаточно выполнить один раз до цикла, а не внутри него — это и быстрее, и понятнее.
Вторая распространённая проблема — путаница между таблицей значений и структурой. У структуры нет коллекции колонок; наличие ключа в ней проверяется методом Свойство("ИмяКлюча", НайденноеЗначение). Попытка вызвать Колонки.Найти() у структуры завершится ошибкой.
Третий нюанс — работа с динамически создаваемыми реквизитами формы. Колонка таблицы значений на форме и реквизит формы — не одно и то же. Если таблица выведена на форму, изменение её колонок требует использования методов ИзменитьРеквизиты(), а проверка наличия реквизита формы выполняется через массив ПолучитьРеквизиты().
Когда проверка не нужна и какие есть альтернативы
Если таблица значений создаётся полностью в вашем коде и её структура фиксирована, проверка наличия колонки избыточна — состав колонок известен на этапе разработки. Лишние проверки только усложняют чтение кода.
Проверка оправдана в трёх случаях: загрузка данных из внешних источников (Excel, CSV, обмены), универсальные обработки для разных конфигураций и динамическое формирование запросов или таблиц. Именно там структура данных может отличаться от ожидаемой.
Альтернативный подход — конструкция Попытка...Исключение. Иногда проще выполнить обращение к колонке внутри попытки и обработать исключение. Однако явная проверка через Найти() предпочтительнее: она быстрее, понятнее и не маскирует другие возможные ошибки внутри блока попытки.
Сравнение вариантов
Основной способ для таблиц, деревьев и результатов запросов. Быстро, явно, без побочных эффектов
Подходит как страховка, но скрывает причину ошибки и медленнее при массовых срабатываниях
Единственный вариант для табличных частей и реквизитов объектов конфигурации
Применяется для структур и соответствий вместо поиска по колонкам
Что важно запомнить
Существование колонки в таблице значений, дереве значений или результате запроса проверяется методом Колонки.Найти() со сравнением результата с Неопределено. Для структур используйте метод Свойство(), для табличных частей — поиск реквизита в метаданных. Проверку выполняйте один раз до цикла обработки.
Частые вопросы
Учитывает ли метод Найти регистр имени колонки?
Нет, поиск по имени колонки в коллекции колонок нечувствителен к регистру. Имена «Сумма», «СУММА» и «сумма» считаются одинаковыми, как и везде во встроенном языке 1С.
Как проверить сразу несколько колонок?
Переберите массив требуемых имён в цикле и для каждого вызовите Колонки.Найти(). Если хотя бы одна колонка отсутствует, можно прекратить обработку и сообщить, каких именно полей не хватает, — так диагностика проблемы будет проще.
Что вернёт Найти, если передать пустую строку?
Метод вернёт Неопределено, так как колонки с пустым именем в таблице значений существовать не может. Платформа не позволяет создать колонку без имени.
Как проверить наличие колонки в динамическом списке на форме?
У динамического списка нет программно доступной коллекции колонок данных. Состав полей определяется его запросом — проверять нужно текст запроса или выгрузить данные в таблицу значений через схему компоновки и уже там использовать Колонки.Найти().
Можно ли проверить колонку у таблицы, полученной из значения в строку?
Да, если значение было сериализовано и восстановлено как таблица значений, у него сохраняется коллекция колонок, и метод Найти() работает обычным образом. Проверка нужна, потому что состав колонок мог измениться между сохранением и загрузкой.
Чем отличается проверка колонки от проверки ключа структуры?
У таблицы значений колонка — элемент коллекции Колонки, проверяется методом Найти(). У структуры данные хранятся как пары «ключ-значение», и наличие ключа проверяется методом Свойство(), который возвращает Истина или Ложь и может сразу вернуть значение ключа.