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

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

Чем структура отличается от соответствия в 1С

Разбираем отличия структуры и соответствия в 1С: фиксированные и произвольные ключи, типы ключей, типовые сценарии применения, примеры кода и частые ошибки.

Структура и соответствие — два базовых типа коллекций во встроенном языке 1С, которые хранят пары «ключ — значение». Внешне они похожи: обе позволяют обращаться к элементам, перебирать их в цикле и передавать между процедурами. Из-за этого сходства начинающие разработчики часто используют их как взаимозаменяемые, что приводит к ошибкам времени выполнения и запутанному коду.

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

Правильный выбор между этими типами влияет не только на читаемость кода, но и на его устойчивость: обращение к несуществующему ключу структуры вызывает исключение, тогда как в соответствии та же операция вернёт Неопределено. Ниже разберём различия по каждому аспекту и покажем, когда какой тип применять.

Состав ключей: фиксированный против динамического

Ключи структуры задаются один раз — в конструкторе Новый Структура("Код, Наименование, Цена"). После создания удалить ключ нельзя, а добавление новых ключей возможно только через метод Вставить(), и это считается признаком сомнительной архитектуры: структура по своей природе описывает фиксированный контракт данных.

В соответствии ключи добавляются и удаляются свободно: Вставить(Ключ, Значение) и Удалить(Ключ) работают в любой момент времени. Коллекция может начинаться пустой и наполняться по мере выполнения алгоритма — например, при построении индекса по товарам из результата запроса.

Практический признак выбора прост: если вы можете перечислить все поля при написании кода — это структура. Если набор ключей определяется данными во время выполнения (ссылки, коды из базы, значения из файла) — это соответствие.

Типы ключей: только строки против любых значений

В структуре ключом может быть только строка, причём она должна удовлетворять правилам именования переменных: начинаться с буквы, не содержать пробелов и специальных символов. Попытка создать структуру с ключом «Код товара» или «123» приведёт к ошибке.

В соответствии ключом может быть значение любого типа: строка с пробелами, число, дата, ссылка на справочник или документ, и даже значение Неопределено. Именно это делает соответствие незаменимым для организации быстрого поиска по ссылкам — например, когда нужно по ссылке на контрагента мгновенно получить накопленные по нему данные без повторного обращения к запросу.

Из этого различия следует важное следствие: если вам нужно сопоставить объекты базы данных с какими-либо вычисленными значениями, структура в принципе не подходит — ссылку нельзя использовать как её ключ.

Способы обращения к элементам

Структура поддерживает два синтаксиса доступа: через точку (Данные.Наименование) и через квадратные скобки (Данные["Наименование"]). Обращение через точку делает код похожим на работу с объектом и удобно, когда имя поля известно на этапе написания кода. Однако при обращении к несуществующему ключу структура выбрасывает исключение «Поле объекта не обнаружено».

Соответствие допускает обращение только через квадратные скобки: Кэш[СсылкаНаТовар]. Обращение к отсутствующему ключу не вызывает ошибки — возвращается Неопределено. Это одновременно удобно и опасно: опечатка или пустой ключ не приведут к явной ошибке, а тихо вернут пустое значение, которое может попасть в дальнейшие расчёты.

Для безопасной проверки наличия ключа используются разные подходы. У структуры есть метод Свойство("Имя", НайденноеЗначение), который возвращает Истина, если ключ существует. У соответствия применяется прямое обращение с последующей проверкой результата на Неопределено.

Структура или соответствие

Структура

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

Соответствие

Подходит для кэшей, индексов поиска по ссылкам, подсчёта значений по произвольным ключам. Ограничение: нет доступа через точку, обращение к отсутствующему ключу молча возвращает Неопределено.

Типовые сценарии применения

Когда использовать структуру

Структура — стандартный инструмент для передачи параметров. Вместо процедуры с десятью параметрами объявляют один параметр-структуру с именованными полями: это упрощает вызов и позволяет добавлять новые поля без изменения сигнатуры. Типовые решения 1С повсеместно используют этот приём — например, параметры открытия форм передаются именно структурой.

Второй сценарий — описание одной строки данных: реквизиты товара, настройки отчёта, результат проверки. Здесь состав полей известен заранее и одинаков для всех экземпляров, что идеально соответствует природе структуры.

Когда использовать соответствие

Соответствие применяют там, где нужен быстрый поиск по произвольному ключу: кэш уже обработанных ссылок, чтобы не выполнять повторные запросы; индекс строк таблицы значений по ключевому полю; подсчёт количества вхождений значений. Классический пример — обход результата запроса с накоплением итогов по контрагентам: ключом служит ссылка, значением — накопленная сумма.

Ещё один сценарий — проверка уникальности: перед добавлением элемента в список проверяют Если УжеОбработано[Ссылка] = Неопределено Тогда .... Это работает существенно быстрее поиска методом Найти() по массиву или таблице значений на больших объёмах данных.

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

Сериализация, JSON и связанные ограничения

Структура напрямую преобразуется в JSON и обратно штатными средствами платформы (ЗаписатьJSON, ПрочитатьJSON), потому что её ключи-строки естественно отображаются на поля JSON-объекта. Соответствие при чтении JSON тоже может использоваться — метод ПрочитатьJSON с параметром ПрочитатьВСоответствие = Истина возвращает именно соответствие, что бывает нужно, когда имена полей во входящем JSON неизвестны заранее.

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

Ещё одно отличие касается фиксированных вариантов: на базе структуры создаётся ФиксированнаяСтруктура, которую нельзя изменить после создания, — она применяется, например, в параметрах форм. Аналогично существует ФиксированноеСоответствие. Попытка изменить фиксированную коллекцию вызывает исключение.

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

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

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

Третья ошибка — молчаливое получение Неопределено из соответствия без проверки. Значение Неопределено, попавшее в арифметическое выражение или запрос, приводит либо к исключению дальше по коду, либо к некорректным данным, которые сложно отладить. Всегда проверяйте результат обращения к соответствию, если наличие ключа не гарантировано логикой алгоритма.

Типичные ошибки
01
Обращение к ключу структуры через точку без проверки Свойство() — исключение «Поле объекта не обнаружено» при отсутствии ключа
02
Использование результата обращения к соответствию без проверки на Неопределено — скрытые ошибки в расчётах
03
Попытка использовать ссылку как ключ структуры — ошибка, ключом структуры может быть только строка-идентификатор
04
Передача соответствия вместо структуры как параметров процедуры — код теряет читаемость, состав полей не виден из вызова

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

После выбора типа коллекции и написания кода полезно пройти несколько контрольных точек. Убедитесь, что все обращения к структуре, где наличие ключа не гарантировано, защищены методом Свойство(). Для соответствия проверьте, что каждый результат обращения либо проверяется на Неопределено, либо наличие ключа обеспечено предшествующей логикой — и это задокументировано комментарием.

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

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

Как проверить корректность кода

Обращения к полям структуры
Норма

Необязательные поля читаются через Свойство() с проверкой результата

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

Прямое обращение через точку к полям, которые могут отсутствовать

Обращения к соответствию
Норма

Результат проверяется на Неопределено перед использованием

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

Значение из соответствия сразу идёт в расчёт или запрос

Выбор типа коллекции
Норма

Ключи-ссылки и произвольные строки — в соответствии, именованные параметры — в структуре

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

Соответствие используется как набор именованных параметров процедуры

Итог

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

Структура — фиксированный набор строковых ключей для именованных параметров и описания данных; соответствие — динамическая коллекция с ключами любого типа для поиска, кэшей и индексов. Структура при отсутствии ключа вызывает исключение, соответствие молча возвращает Неопределено — обе особенности требуют защитных проверок в коде.

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

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

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

Что быстрее работает — структура или соответствие?

Обе коллекции построены на хеш-таблицах и обеспечивают быстрый доступ по ключу. Разница в производительности между ними в типовых прикладных задачах несущественна, поэтому выбирать тип следует по семантике данных, а не по скорости. Реальный выигрыш соответствие даёт по сравнению с поиском методом Найти() в массиве или таблице значений на больших объёмах.

Как проверить, есть ли ключ в соответствии, если значением может быть Неопределено?

Если вы сами записывали Неопределено как значение, то проверка Если Кэш[Ключ] = Неопределено не отличит отсутствующий ключ от ключа со значением Неопределено. В таких случаях в качестве значения сохраняют маркер (например, Истина или структуру-обёртку) либо ведут учёт наличия ключей отдельно.

Чем фиксированная структура отличается от обычной?

ФиксированнаяСтруктура создаётся на базе обычной и после создания не позволяет изменять значения ключей, добавлять или удалять их — любая попытка вызывает исключение. Она применяется для неизменяемых наборов параметров, например платформа использует её в параметрах форм и настройках компоновки данных.

Можно ли сериализовать соответствие в JSON?

Напрямую записать соответствие в JSON штатный сериализатор не сможет, если ключи не строковые, поскольку JSON-объект предполагает строковые имена полей. На практике соответствие перед записью преобразуют в массив структур вида «Ключ/Значение» либо в структуру, если ключи позволяют. Чтение JSON в соответствие, наоборот, поддерживается штатно.

Что использовать для параметров запроса — структуру или соответствие?

Для установки параметров запроса ни одна из коллекций не требуется напрямую: параметры задаются методом УстановитьПараметр("Имя", Значение). Однако структуру удобно использовать как промежуточный контейнер: собрать параметры в структуру, а затем перебрать её в цикле и установить каждый параметр запроса — это делает код компактнее и исключает пропуск параметра.