В стандартах разработки 1С существует строгое правило: не рекомендуется обращаться к реквизитам объектов через точку от ссылки (особенно через две и более точки). У разработчиков часто возникает вопрос, распространяется ли это правило на элементы управляемой формы и как правильно адресовать элементы интерфейса для максимальной производительности. Разберем детально, как устроена работа с элементами формы и в чем принципиальная разница между обращением к данным базы и объектам интерфейса.
Коллекция Элементы в управляемой форме кардинально отличается от иерархических структур данных базы. Коллекция элементов является плоской. Это означает, что все поля ввода, группы, таблицы, командные панели и колонки таблиц располагаются на одном общем уровне адресации, независимо от того, как они визуально вложены в дереве элементов формы.
Посмотрим на пример ошибочного обращения, когда разработчик пытается повторить визуальную иерархию формы:
// Ошибочная попытка обращения через родительскую таблицу или группу:
Элементы.Товары.Номенклатура.Видимость = Ложь; // Вызовет исключение «Поле объекта не обнаружено»
Объект ТаблицаФормы или ГруппаФормы не содержит подчиненных элементов в виде собственных свойств. Любая колонка или вложенное поле доступны напрямую из корневой коллекции формы:
// Корректное прямое обращение:
Элементы.Номенклатура.Видимость = Ложь;
// Либо программное обращение по имени через скобки:
Элементы["Номенклатура"].Видимость = Ложь;
Обращение по индексу Элементы["ИмяЭлемента"] работает немного медленнее прямого обращения через точку Элементы.ИмяЭлемента из-за поиска по строковому ключу, однако оно удобно для динамических проверок при использовании метода Элементы.Найти().
Чтобы понять происхождение стандартов, проанализируем, что происходит при обращении через точку к ссылочным типам данных базы (справочники, документы и т.д.):
// Неоптимальный код:
СтранаСсылка = Объект.Контрагент.СтранаРегистрации; // Разыменование через две точки
КодСтраны = СтранаСсылка.Код;
При первом обращении к реквизиту через ссылку платформа 1С считывает из базы данных весь объект целиком вместе со всеми его реквизитами и табличными частями. Если в дальнейшем читать другие реквизиты подряд, сработает объектный кэш текущего сеанса, и повторных обращений к СУБД для этого объекта не будет. Однако первоначальная загрузка избыточных данных создает существенную нагрузку на память и сеть.
Если же разыменование идет через цепочку связанных объектов (например, Документ.Контрагент.ОсновнойДоговор.ВалютаВзаиморасчетов), платформа будет последовательно загружать в память каждый промежуточный объект целиком, генерируя серию отдельных запросов.
Для чтения отдельных реквизитов без избыточного чтения объектов стандарт 1С предписывает использовать прямой запрос или функции БСП:
// Оптимальное получение значений через БСП:
Значения = ОбщегоНазначения.ЗначенияРеквизитовОбъекта(СсылкаНаОбъект, "Код, Наименование, ИНН");
Код = Значения.Код;
ИНН = Значения.ИНН;
Так как элементы формы находятся исключительно в оперативной памяти клиента или сервера и не обращаются к физическим таблицам СУБД, проблема цепочки точек к ним не относится. Однако медленная работа форм вызывается другими факторами, которые мы разберем по шагам.
ПриСозданииНаСервере или ПриЧтенииНаСервере. В этом случае клиент получает уже готовую структуру за один сетевой пакет.УсловноеОформление, чем менять свойства элементов вручную из клиентских событий. Условное оформление можно настраивать как интерактивно, так и программно на сервере.&НаСервере передают на сервер все данные формы (контекст). Для вспомогательных расчетов и проверок всегда используйте вызовы &НаСервереБезКонтекста, передавая только необходимые параметры.Обращение через несколько точек к элементам формы невозможно из-за плоской структуры коллекции Элементы. Контроль количества точек и использование специализированных функций выборки требуются только при работе со ссылочными данными информационной базы, в то время как производительность форм обеспечивается грамотным распределением контекста между клиентом и сервером.