Почему объект ПостроительОтчета инициализирован при открытии формы без явного вызова конструктора

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

При разработке в среде «1С:Предприятие 8» (особенно в режиме «Обычного приложения») программисты часто сталкиваются с ситуацией, которая на первый взгляд кажется магической: в первой же строке обработчика ПередОткрытием сложный объект, такой как ПостроительОтчета, уже создан, имеет тип и готов к работе. При этом в коде модуля нет ни одной строки вида ПостроительОтчета = Новый ПостроительОтчета. Разберемся по шагам, как устроена внутренняя механика платформы и почему это происходит.

Анализ механизма автоматического инстанцирования

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

Этот процесс происходит на этапе выделения памяти под структуру формы, еще до того, как управление передается в программный модуль. Рассмотрим последовательность событий при открытии формы:

  1. Выделение памяти: Платформа считывает описание формы из метаданных.
  2. Инициализация реквизитов: Для каждого реквизита создается переменная. Если тип реквизита — простой (Число, Строка), ему присваивается значение по умолчанию. Если тип — сложный (ТаблицаЗначений, ПостроительОтчета, СписокЗначений), платформа автоматически создает экземпляр этого объекта.
  3. Восстановление настроек: Если включено свойство «Сохраняемые значения», данные загружаются из хранилища.
  4. Передача управления в код: Вызывается процедура ПередОткрытием.

Именно поэтому, поставив точку останова в самом начале модуля, мы видим уже «живой» объект.

Различие между реквизитами формы и переменными модуля

Важно четко различать реквизиты формы (описанные в редакторе на закладке «Реквизиты») и переменные, объявленные в коде. Проанализируем пример кода, чтобы увидеть разницу в их поведении:


// Это переменная модуля
Перем МойПостроительПрограммный; 

Процедура ПередОткрытием(Отказ, СтандартнаяОбработка)
    // Реквизит формы "ПостроительОтчета" уже инициализирован платформой
    Сообщить(ТипЗнч(ПостроительОтчета)); // Выведет: Построитель отчета
    
    // Переменная модуля будет иметь значение Неопределено
    Сообщить(ТипЗнч(МойПостроительПрограммный)); // Выведет: Неопределено
    
    // Для переменной конструктор НУЖЕН:
    МойПостроительПрограммный = Новый ПостроительОтчета;
КонецПроцедуры

Таким образом, если вы объявили объект в визуальном редакторе формы, писать Новый не только не обязательно, но и вредно, так как это приведет к пересозданию объекта и лишним затратам ресурсов.

Типизация и значения по умолчанию

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

Как было верно замечено в обсуждении, если значение равно NULL — это обычно результат запроса. Если значение Неопределено — это признак того, что тип либо еще не назначен (составной тип), либо это переменная, которой не присвоили значение. Реквизит формы типа ПостроительОтчета не может быть ни тем, ни другим — он сразу становится объектом своего типа.

Влияние свойства «Сохраняемые значения»

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

Сравнение с Управляемыми формами

Стоит отметить, что в современных «Управляемых формах» (платформа 8.3) подход изменился. Тип ПостроительОтчета является чисто серверным. Он не может быть реквизитом управляемой формы напрямую. Вместо него используются КомпоновкаДанных или данные формы, которые трансформируются в объекты только при вызове серверных процедур. Если вы переходите с обычных форм на управляемые, помните: там явная инициализация объектов на сервере через Новый встречается гораздо чаще.

Практические следствия для разработчика

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

  1. Не дублируйте конструктор: Не пишите ПостроительОтчета = Новый ПостроительОтчета для реквизитов формы. Это создает лишний объект в памяти, который тут же будет удален сборщиком мусора, так как ссылка на него будет заменена.
  2. Используйте типизацию: Сразу обращайтесь к свойствам объекта, например: ПостроительОтчета.Текст = "ВЫБРАТЬ...".
  3. Проверяйте стек вызовов: Если вам кажется, что код всё же где-то выполняется, используйте «Замер производительности». Однако помните: автоматическую инициализацию реквизитов замер не покажет, так как это внутренняя работа ядра платформы.

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

← На главную