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