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

Что такое переменная в 1С?
Переменная — это именованная область памяти, в которой хранится значение. В 1С переменные являются динамически типизированными: вам не нужно заранее указывать, какой тип данных будет в ней лежать. Одна и та же переменная может сначала содержать число, потом строку, а затем дату.
Объявить переменную можно явно с помощью ключевого слова Перем, либо неявно — просто присвоив ей значение:
// Явное объявлениеПерем Счётчик;
// Неявное объявление через присваивание
Счётчик = 0;
Имя = "Алексей";
ДатаНачала = '20250101';Если переменная объявлена через Перем, но ей ещё не присвоено значение, она содержит специальное значение Неопределено. Это важный момент: Неопределено — это не ноль, не пустая строка и не ошибка. Это самостоятельный тип данных, означающий отсутствие значения.
Область видимости: где живёт переменная
В 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 участников делятся опытом и помогают друг другу расти в профессии.
