Как изменить размер массива в 1С и есть ли аналог ReDim Preserve из VBA?

Программист 1С v8.3 (Обычные формы) IT и автоматизация бизнеса
← На главную

Разработчики, переходящие в среду 1С:Предприятие из других языков программирования (например, Visual Basic или VBA), часто ищут привычные инструменты для управления памятью и коллекциями. Одним из таких инструментов является инструкция ReDim Preserve, которая позволяет динамически изменять размерность существующего массива, сохраняя при этом все накопленные в нем данные. В этой статье мы подробно разберем, как устроены массивы в 1С, как правильно управлять их размером и какие альтернативные объекты платформы можно использовать для решения подобных задач.

Динамическая природа массивов в 1С

Начнем с главного отличия платформ: в 1С все стандартные массивы по умолчанию являются динамическими. Нам не требуется заранее жестко объявлять размерность массива для последующей работы с ним (как это делается в классическом статическом VB). Платформа 1С берет на себя управление выделением оперативной памяти под новые элементы.

Если нам необходимо добавить новый элемент в конец массива, мы не переопределяем его размер заново, а просто используем встроенный метод Добавить(). Посмотрим на простой пример создания и наполнения одномерного массива:


// Создаем пустой массив с нулевым количеством элементов
ДинамическийМассив = Новый Массив;

// Последовательно наполняем его данными
ДинамическийМассив.Добавить("Значение 1");
ДинамическийМассив.Добавить("Значение 2");
ДинамическийМассив.Добавить("Значение 3");

Каждый вызов метода Добавить() автоматически увеличивает размер коллекции на единицу, сохраняя все ранее записанные значения. Таким образом, классический аналог связки переопределения размерности в VBA здесь попросту не нужен.

Инициализация массива фиксированной длины

Иногда алгоритм требует, чтобы массив изначально имел определенное количество ячеек (например, 12 элементов для месяцев года), к которым мы будем обращаться напрямую по их индексам. В 1С это реализуется при помощи передачи параметров в конструктор Новый Массив. Проанализируем пример инициализации:


// Создаем массив, сразу содержащий 12 элементов
МассивМесяцев = Новый Массив(12);

// Теперь мы можем обращаться к элементам по индексу
МассивМесяцев[0] = "Январь";
МассивМесяцев[11] = "Декабрь";

Важное ограничение платформы: В 1С индексы элементов массива всегда начинаются строго с 0. Задать произвольный диапазон индексов (например, от 1 до 12, как это позволяет конструкция 1 To 12 в VBA) невозможно. Первый элемент всегда будет иметь индекс 0, а последний — индекс Количество() - 1.

Реализация аналога ReDim Preserve для изменения размера

У объекта Массив в 1С нет прямого метода, позволяющего одной строкой кода изменить текущую длину до конкретного значения (например, уменьшить массив с 10 элементов до 5 или увеличить до 15). Тем не менее мы можем легко реализовать это поведение самостоятельно.

Вариант 1. Увеличение размера массива (Расширение)

Если нам нужно гарантированно расширить существующий массив до определенного размера, сохранив старые значения, а новые ячейки заполнить пустыми значениями (Неопределено), мы можем использовать простой цикл:


// Исходный массив из 3 элементов
МойМассив = Новый Массив;
МойМассив.Добавить("А");
МойМассив.Добавить("Б");
МойМассив.Добавить("В");

ТребуемыйРазмер = 7; // Хотим расширить массив до 7 элементов

// Добавляем новые пустые элементы, пока не достигнем нужного размера
Пока МойМассив.Количество() < ТребуемыйРазмер Цикл
    МойМассив.Добавить(Неопределено);
КонецЦикла;

Вариант 2. Уменьшение размера массива (Обрезание с конца)

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

Если начать удалять элементы с начала или середины коллекции, индексы оставшихся элементов динамически сдвинутся влево, что приведет к ошибкам позиционирования или выходу за границы в процессе работы цикла. Для безопасного обрезания мы задействуем метод ВГраница(), возвращающий максимальный индекс в массиве:


// Исходный массив из 5 элементов
МойМассив = Новый Массив;
МойМассив.Добавить("Элемент 1");
МойМассив.Добавить("Элемент 2");
МойМассив.Добавить("Элемент 3");
МойМассив.Добавить("Элемент 4");
МойМассив.Добавить("Элемент 5");

ТребуемыйРазмер = 3; // Хотим оставить только первые 3 элемента

// Удаляем элементы с конца, пока размер не уменьшится до требуемого
Пока МойМассив.Количество() > ТребуемыйРазмер Цикл
    ИндексКонца = МойМассив.ВГраница();
    МойМассив.Удалить(ИндексКонца);
КонецЦикла;

Альтернативные структуры данных в 1С

Если логика вашей программы завязана на работу со сложными или разреженными ключами, стандартный массив может оказаться не лучшим выбором. Платформа предлагает более специализированные коллекции.

  1. Объект «Соответствие» (Map): Идеально подходит, если вам требуется задать произвольный диапазон ключей (например, от 1 до 12) или использовать в качестве ключей строки/объекты. Данный объект хранит пары "Ключ - Значение", работает быстро и не требует последовательного заполнения всех промежуточных элементов.
  2. Объект «ТаблицаЗначений»: Мощный инструмент для работы на стороне сервера. Она позволяет динамически добавлять строки и колонки, сортировать данные, находить дубликаты методом Свернуть() или мгновенно выгружать значения отдельных колонок обратно в массив с помощью метода ВыгрузитьКолонку().

Резюмируя, можно сказать, что явного аналога ReDim Preserve в 1С нет, поскольку философия работы с динамической памятью здесь иная. Благодаря встроенным динамическим свойствам массивов и простым циклам обрезания/добавления, любые манипуляции с размерностью коллекций реализуются прозрачно и надежно.

← На главную