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