{}const=>[]async()letfn</>var
1CEntwicklung

Переменные и типы данных в 1С: что хранится в памяти и почему это важно

Разбираемся, как устроены переменные и типы данных во встроенном языке 1С — от примитивных типов и области видимости до ссылочных типов, коллекций и подводных камней с приведением типов. Практические примеры и советы по оптимизации.

К

Kodik

Autor

calendar_today
schedule8 Min. Lesezeit

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

Что такое переменная в 1С?

Переменная — это именованная область памяти, в которой хранится значение. В 1С переменные являются динамически типизированными: вам не нужно заранее указывать, какой тип данных будет в ней лежать. Одна и та же переменная может сначала содержать число, потом строку, а затем дату.

Объявить переменную можно явно с помощью ключевого слова Перем, либо неявно — просто присвоив ей значение:

// Явное объявлениеПерем Счётчик;

// Неявное объявление через присваивание
Счётчик = 0;
Имя = "Алексей";
ДатаНачала = '20250101';

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

🔥 100.000+ Schüler sind bereits bei uns

Genug Theorie gelesen?
Zeit zu coden!

Kodik — eine App, in der du durch Praxis programmieren lernst. KI-Mentor, interaktive Lektionen, echte Projekte.

🤖 KI 24/7
🎓 Zertifikate
💰 Kostenlos
🚀 Jetzt starten
Heute beigetreten

Область видимости: где живёт переменная

В 1С существует три уровня видимости переменных.

Переменные модуля объявляются в самом начале модуля (до процедур и функций) через Перем. Они доступны из любой процедуры и функции этого модуля и существуют, пока существует сам модуль. Это аналог глобальных переменных внутри одного объекта.

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

Экспортные переменные — это переменные модуля, помеченные ключевым словом Экспорт. Они доступны извне — из других модулей и форм:

Перем ГлобальнаяНастройка Экспорт;

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

Примитивные типы данных

Платформа 1С предоставляет несколько базовых (примитивных) типов, которые являются строительными блоками для всего остального.

Число — хранит целые и дробные числа. Максимальная разрядность — 38 знаков, из которых до 10 могут быть после запятой. 1С использует десятичную арифметику, а не двоичную с плавающей точкой, как большинство языков программирования. Это означает, что 0.1 + 0.2 в 1С даст ровно 0.3, а не 0.30000000000000004, как в JavaScript или Python. Для финансовых расчётов это критически важное свойство:

Цена = 1500.50;
Количество = 3;
Сумма = Цена * Количество; // 4501.50 — точно, без погрешностей

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

// Плохо — квадратичная сложность по памяти
Результат = "";
Для Каждого Элемент Из Коллекция Цикл
    Результат = Результат + Элемент + ", ";
КонецЦикла;

// Лучше — линейная сложность
Части = Новый Массив;
Для Каждого Элемент Из Коллекция Цикл
    Части.Добавить(Элемент);
КонецЦикла;
Результат = СтрСоединить(Части, ", ");

Дата — хранит дату и время с точностью до секунды. Пустая дата — это '00010101', а не Неопределено. Это частый источник ошибок: проверка Если Дата = Неопределено не поймает пустую дату. Правильная проверка:

Если ДатаДокумента = '00010101' Тогда
    // Дата не заполненаКонецЕсли;

Булево — принимает значения Истина или Ложь. В условных выражениях 1С не выполняет неявного приведения типов: число 0 не превращается автоматически в Ложь, как в JavaScript. Нужно писать явное сравнение.

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

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

Ссылочные типы: что на самом деле лежит в переменной?

Когда вы получаете элемент справочника или документ, в переменной хранится не сам объект целиком, а ссылка — уникальный идентификатор (UUID), по которому платформа может найти данные в базе:

СсылкаНаТовар = Справочники.Товары.НайтиПоКоду("00001");

Переменная СсылкаНаТовар содержит ссылку типа СправочникСсылка.Товары. Это компактный объект — по сути, обёртка над GUID. Сами данные (наименование, цена, остатки) в память не загружены. Они подтянутся из базы данных только при первом обращении к реквизиту:

// Именно здесь происходит обращение к базе данных
Наименование = СсылкаНаТовар.Наименование;

Это называется ленивая загрузка (lazy loading), и у неё есть обратная сторона. Если вы в цикле обходите тысячу ссылок и у каждой читаете реквизит через точку, платформа выполнит тысячу отдельных запросов к базе. Правильное решение — получать данные пакетно через запрос:

// Плохо — 1000 обращений к базеДля Каждого Ссылка Из МассивСсылок Цикл
    Наименование = Ссылка.Наименование; // запрос к БД на каждой итерацииКонецЦикла;

// Хорошо — 1 запрос к базе
Запрос = Новый Запрос;
Запрос.Текст = "ВЫБРАТЬ Наименование ИЗ Справочник.Товары ГДЕ Ссылка В (&Список)";
Запрос.УстановитьПараметр("Список", МассивСсылок);
Результат = Запрос.Выполнить().Выгрузить();

Важно: Ссылка (СправочникСсылка) — это «указатель» на данные, доступный только для чтения. Объект (СправочникОбъект) — это полная загруженная в память копия данных, которую можно изменять и записывать. Объект тяжелее ссылки. Если вы получаете объекты в цикле, но не собираетесь их изменять — используйте ссылки и запросы.

// Получаем объект — все данные загружены в память
ОбъектТовара = СсылкаНаТовар.ПолучитьОбъект();
ОбъектТовара.Наименование = "Новое название";
ОбъектТовара.Записать();

Составной тип: одно поле — много возможностей

В метаданных 1С реквизит может иметь составной тип. Например, поле «Владелец» в документе может быть одновременно типа СправочникСсылка.Организации и СправочникСсылка.ФизическиеЛица. Платформа хранит в этом поле и само значение, и информацию о его типе.

Для работы с составными типами используется объект ОписаниеТипов:

МассивТипов = Новый Массив;
МассивТипов.Добавить(Тип("Число"));
МассивТипов.Добавить(Тип("Строка"));

ОписаниеДопустимыхТипов = Новый ОписаниеТипов(МассивТипов);

Проверить текущий тип значения в переменной можно функцией ТипЗнч():

Если ТипЗнч(Значение) = Тип("Число") Тогда
    // Работаем как с числомИначеЕсли ТипЗнч(Значение) = Тип("СправочникСсылка.Товары") Тогда
    // Работаем как со ссылкойКонецЕсли;

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

Коллекции: массивы, структуры и соответствия

Помимо примитивных и ссылочных типов, в 1С есть набор универсальных коллекций, которые используются повсеместно.

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

Список = Новый Массив;
Список.Добавить(42);
Список.Добавить("текст");
Список.Добавить(ТекущаяДата());

Структура — набор пар «ключ-значение», где ключи — это строки, заданные при создании. Структура удобна для передачи именованных параметров:

Параметры = Новый Структура;
Параметры.Вставить("Организация", СсылкаОрганизации);
Параметры.Вставить("Период", ТекущаяДата());

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

КэшНаименований = Новый Соответствие;
КэшНаименований.Вставить(СсылкаНаТовар, "Молоко 3.2%");
Наименование = КэшНаименований.Получить(СсылкаНаТовар); // "Молоко 3.2%"

Нюанс: Метод Получить у соответствия возвращает Неопределено, если ключ не найден, а не вызывает ошибку. Это нужно учитывать при написании условий.

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

ТЗ = Новый ТаблицаЗначений;
ТЗ.Колонки.Добавить("Товар", Новый ОписаниеТипов("СправочникСсылка.Товары"));
ТЗ.Колонки.Добавить("Количество", Новый ОписаниеТипов("Число"));

НоваяСтрока = ТЗ.Добавить();
НоваяСтрока.Товар = СсылкаНаТовар;
НоваяСтрока.Количество = 10;

Таблица значений может занимать значительный объём памяти. Если вы выгружаете в неё результат запроса с миллионом строк, вся эта информация окажется в оперативной памяти сервера. Для больших объёмов данных лучше обрабатывать результат запроса порционно через Выборка, а не загружать всё в таблицу разом.

Приведение типов и подводные камни

1С выполняет неявное приведение типов в некоторых операциях, и это может приводить к неожиданным результатам:

// Строка + Число — будет ошибка!
Результат = "Итого: " + 100; // Ошибка приведения типа

// Правильно — явное приведение
Результат = "Итого: " + Строка(100); // "Итого: 100"

// Сравнение разных типовЕсли 0 = Ложь Тогда   // Ложь — типы не совпадаютКонецЕсли;

Если 0 = "" Тогда     // Тоже ЛожьКонецЕсли;

Функции явного приведения — ваши друзья: Число(), Строка(), Дата(), Булево(). Используйте их всегда, когда нужно преобразовать значение, и не полагайтесь на автоматику платформы.

Передача параметров: по значению и по ссылке

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

Процедура ДобавитьЭлемент(МойМассив)
    МойМассив.Добавить("новый элемент");
КонецПроцедуры

Данные = Новый Массив;
ДобавитьЭлемент(Данные);
// Данные теперь содержит "новый элемент"

Если вы хотите защитить оригинал от изменений, используйте ключевое слово Знач:

Процедура БезопаснаяОбработка(Знач МойМассив)
    МойМассив.Добавить("это не повлияет на оригинал");
КонецПроцедуры

Однако для примитивных типов (число, строка, дата, булево) передача «по ссылке» работает иначе: переприсваивание параметра внутри процедуры не влияет на внешнюю переменную. Изменения видны только для мутабельных объектов — массивов, структур, таблиц значений.

Почему всё это важно?

Понимание переменных и типов данных — это не академическое упражнение. Это напрямую влияет на качество вашего кода. Знание того, что строки неизменяемы, спасёт от создания тысяч промежуточных объектов в памяти. Понимание разницы между ссылкой и объектом предотвратит сотни лишних запросов к базе данных. Осознание того, как работают составные типы, поможет правильно проектировать структуру метаданных. А чёткое представление об области видимости убережёт от утечек памяти в серверном коде.

Каждый раз, когда вы объявляете переменную, вы принимаете архитектурное решение: что хранить, где хранить и как долго. Чем лучше вы понимаете внутреннюю механику платформы, тем увереннее и эффективнее будет ваш код.


Если вы хотите изучать программирование системно — от основ до продвинутых тем — загляните в приложение Кодик. Это образовательная платформа с пошаговыми курсами по Python, JavaScript, HTML, CSS и другим языкам, которая поможет вам выстроить прочный фундамент знаний.

А если возникнут вопросы или захочется обсудить материал с другими разработчиками — присоединяйтесь к нашему Telegram-каналу, где уже более 2000 участников делятся опытом и помогают друг другу расти в профессии.

🎯Hör auf zu zögern

Artikel gefallen?
Zeit zum Üben!

Bei Kodik liest du nicht nur — du schreibst sofort Code. Theorie + Praxis = echte Skills.

Sofortige Praxis
🧠KI erklärt Code
🏆Zertifikat

Keine Registrierung • Keine Karte