Разработка и Конфигурация · 11 мин
Как сделать массив структур в 1С
Как создать массив структур в 1С: объявление, добавление элементов, обход в цикле, поиск и сортировка. Примеры кода, типичные ошибки и отличия от таблицы значений.
Массив структур — один из самых востребованных приёмов во встроенном языке 1С. Он позволяет хранить набор однотипных записей: строки заказа, данные сотрудников, параметры отбора, результаты обработки — всё то, что удобно описать набором именованных полей, не создавая таблицу значений. Приём прост: создаётся массив, а каждым его элементом становится структура с нужным набором ключей.
Такой подход легче таблицы значений по ресурсам и быстрее пишется, когда не нужны сортировка по нескольким колонкам, итоги и свёртывание. Но у него есть ограничения: у структуры нет предопределённой схемы, поля добавляются динамически, и опечатка в имени ключа не вызовет ошибки компиляции — она проявится только в момент обращения. Поэтому важно сразу договориться о едином наборе ключей для всех элементов массива.
Ниже разобраны создание массива, добавление структур, обход, поиск, изменение элементов, а также ситуации, когда вместо массива структур правильнее использовать таблицу значений или соответствие.
Что такое массив структур и когда он нужен
Массив — упорядоченная коллекция значений с доступом по индексу, начиная с нуля. Структура — коллекция пар «ключ — значение», где ключи задаются строкой при создании. Комбинация «массив структур» даёт аналог списка записей: индекс определяет позицию записи, ключи структуры — её поля.
Типичные сценарии использования: передача набора параметров между процедурами, накопление результатов обхода выборки, формирование данных для последующей сериализации в JSON, временное хранение строк перед записью в регистр или документ. Во всех этих случаях массив структур проще таблицы значений: не нужно описывать колонки, типы и создавать объект с «тяжёлой» внутренней механикой.
Важно понимать ограничение: структура не контролирует типы значений и не проверяет состав ключей. Если в одном элементе массива поле называется «Сумма», а в другом по ошибке «Сума», платформа не сообщит об этом до момента обращения к несуществующему ключу. Дисциплина именования — ответственность разработчика.
Создание массива и добавление структур
Базовый шаблон выглядит так: сначала создаётся пустой массив, затем в него добавляются структуры. Ключи структуры перечисляются строкой через запятую, значения — в том же порядке.
МассивДанных = Новый Массив;
Запись = Новый Структура("Номенклатура, Количество, Цена",
ТекНоменклатура, 2, 1500);
МассивДанных.Добавить(Запись);
Если значения на момент создания неизвестны, можно создать структуру только с ключами — значения будут Неопределено, и их можно заполнить позже. Это удобно, когда поля заполняются поэтапно в разных ветках алгоритма.
- 1Объявите переменную: МассивДанных = Новый Массив;
- 2Определите единый набор ключей для всех элементов и зафиксируйте его в комментарии
- 3Создайте структуру: Новый Структура("Ключ1,Ключ2", Значение1, Значение2)
- 4Добавьте её в массив методом Добавить()
- 5Повторяйте шаги 3–4 для каждой записи, например внутри цикла обхода выборки
- 6Проверьте результат: МассивДанных.Количество() должно совпадать с ожидаемым числом записей
Типичный сценарий — наполнение массива в цикле обхода выборки из запроса. В этом случае структура создаётся на каждой итерации внутри цикла, иначе в массив попадут ссылки на один и тот же объект, и все элементы будут содержать данные последней строки.
Пока Выборка.Следующий() Цикл
Строка = Новый Структура("Ссылка, Сумма, Дата");
Строка.Ссылка = Выборка.Ссылка;
Строка.Сумма = Выборка.Сумма;
Строка.Дата = Выборка.Дата;
МассивДанных.Добавить(Строка);
КонецЦикла;
Обход массива и доступ к полям
Для чтения данных чаще всего используется цикл Для Каждого — он не требует контроля индекса и читается проще. Доступ к полю элемента — через точку, если имя ключа известно на этапе написания кода.
Для Каждого Элемент Из МассивДанных Цикл
Сообщить(Строка(Элемент.Номенклатура) + ": " + Элемент.Количество);
КонецЦикла;
Когда имя ключа формируется динамически или содержит символы, недопустимые для идентификатора, используется обращение через квадратные скобки со строкой: Элемент["Номенклатура"]. Этот же способ применяется, когда нужно проверить наличие ключа методом Свойство() перед обращением.
Если нужен индекс — например, для вывода номера строки или параллельной работы со вторым массивом, — используйте классический цикл со счётчиком, помня, что индексация начинается с нуля, а верхняя граница равна Количество() - 1.
Поиск, изменение и удаление элементов
Встроенного метода поиска по значению поля у массива структур нет — поиск выполняется обходом с условием. Для одиночного поиска это приемлемо; если поиск выполняется многократно в большом объёме, стоит рассмотреть соответствие с ключом по уникальному полю.
Найденный = Неопределено;
Для Каждого Элемент Из МассивДанных Цикл
Если Элемент.Ссылка = ИскомаяСсылка Тогда
Найденный = Элемент;
Прервать;
КонецЕсли;
КонецЦикла;
Изменение элемента выполняется прямым присваиванием полю: поскольку переменная цикла содержит ссылку на структуру, изменения сохраняются в массиве автоматически, повторное добавление не требуется. Удаление — методом Удалить(Индекс). При удалении в цикле обходите массив с конца (от Количество()-1 до 0 с шагом -1), иначе сдвиг индексов приведёт к пропуску элементов.
Массив структур или таблица значений: что выбрать
Выбор зависит от задачи. Таблица значений даёт типизированные колонки, сортировку, поиск через НайтиСтроки, свёртывание и итоги, но требует описания колонок и потребляет больше ресурсов. Массив структур легче и быстрее создаётся, но всю логику поиска и агрегации придётся писать вручную.
Сравнение вариантов
Подходит для передачи параметров, простого накопления записей, сериализации в JSON. Ограничение: нет встроенного поиска, сортировки и контроля типов.
Подходит для многократного поиска, сортировки, группировки и вычисления итогов. Ограничение: требует описания колонок, тяжелее по ресурсам.
Подходит, когда нужен быстрый поиск записи по уникальному ключу. Ограничение: порядок элементов не гарантирован.
Подходит для неизменяемых наборов параметров. Ограничение: состав ключей и значения нельзя менять после создания.
Практическое правило: если данные только накапливаются и один раз обходятся — массив структур; если к ним обращаются многократно с поиском и сортировкой — таблица значений; если нужен мгновенный доступ по ключу — соответствие, где значением может быть та же структура.
Типичные ошибки и проверка результата
Для защиты от обращения к несуществующему ключу используйте метод Свойство(): он возвращает Истина, если ключ есть, и может вернуть значение через второй параметр. Это особенно полезно, когда массив приходит извне — из другой процедуры, обмена или десериализации JSON.
ЗначениеПоля = Неопределено;
Если Элемент.Свойство("Сумма", ЗначениеПоля) Тогда
// работаем со значением
КонецЕсли;
Как проверить результат
МассивДанных.Количество() равно числу обработанных записей
Количество меньше ожидаемого — пропуски в цикле или досрочный Прервать
Каждый элемент содержит данные своей строки источника
Все элементы одинаковые — структура создана вне цикла
У всех элементов одинаковый состав полей
Обращение к полю вызывает ошибку «Поле объекта не обнаружено»
Вложенные структуры и сериализация
Значением ключа структуры может быть другая структура или массив — это позволяет строить иерархические данные: документ с табличной частью, заказ со списком строк. Такой массив структур напрямую преобразуется в JSON через ЗаписьJSON, что делает приём стандартным для интеграций с веб-сервисами.
Документ = Новый Структура("Номер, Дата, Строки",
НомерДок, ДатаДок, Новый Массив);
Для Каждого Стр Из ТабличнаяЧасть Цикл
Документ.Строки.Добавить(
Новый Структура("Товар, Количество", Стр.Товар, Стр.Количество));
КонецЦикла;
При сериализации учитывайте ограничения: в JSON корректно преобразуются примитивные типы, даты (с указанием формата), структуры и массивы. Ссылки на объекты базы напрямую не сериализуются — их нужно предварительно преобразовать в строковое представление уникального идентификатора или наименование.
Что важно запомнить
Массив структур создаётся через Новый Массив и добавление элементов Новый Структура в цикле. Ключевые правила: создавайте структуру на каждой итерации, держите единый набор ключей, удаляйте элементы обходом с конца, для многократного поиска и сортировки переходите на таблицу значений или соответствие.
Частые вопросы
Можно ли отсортировать массив структур по полю?
Встроенной сортировки по полю структуры у массива нет. Варианты: реализовать сортировку вручную, выгрузить данные в таблицу значений и отсортировать её, либо изначально получать данные упорядоченными — например, добавить УПОРЯДОЧИТЬ ПО в запрос, из которого заполняется массив.
Как передать массив структур между клиентом и сервером?
Массивы и структуры сериализуются платформой и свободно передаются между клиентскими и серверными вызовами, если содержат только сериализуемые значения. Внутри не должно быть несериализуемых объектов — например, элементов формы или открытых соединений.
Чем структура отличается от соответствия?
У структуры ключи — допустимые идентификаторы, заданные при создании, обращение возможно через точку. У соответствия ключом может быть значение любого типа, включая ссылки, состав ключей свободно меняется. Для массива записей с фиксированными полями обычно используют структуру, для поиска по произвольному ключу — соответствие.
Как проверить, что массив пустой?
Условие Массив.Количество() = 0. Дополнительно полезно проверять саму переменную на Неопределено, если массив возвращается из функции, которая в некоторых ветках может не создать его.
Можно ли использовать массив структур как источник данных для динамического списка или СКД?
Напрямую — нет. Для СКД внешним набором данных может выступать таблица значений: массив структур сначала выгружается в неё. Для динамического списка источником служит запрос к данным базы, произвольные коллекции он не принимает.
Есть ли ограничение на размер массива структур?
Жёсткого лимита платформа не устанавливает, объём ограничен доступной памятью. На практике при сотнях тысяч элементов стоит пересмотреть подход: обрабатывать данные порциями или использовать запрос и временные таблицы вместо накопления всего объёма в памяти.