Файл: Хрусталева Е. Ю. Язык запросов 1С-Предприятия 8 (2013).pdf

ВУЗ: Не указан

Категория: Не указан

Дисциплина: Не указана

Добавлен: 12.03.2019

Просмотров: 51755

Скачиваний: 8724

ВНИМАНИЕ! Если данный файл нарушает Ваши авторские права, то обязательно сообщите нам.
background image

Но мало того, что запрос запутанный, он еще и неоптимальный. В левой части соединения
используется подзапрос с псевдонимом СоставДокумента. На самом деле не важно, в
какой части соединения (правой или левой) используется подзапрос, также это плохо для
любого вида соединения.

При выполнении такого запроса, независимо от используемой СУБД, весьма вероятны
ошибки оптимизатора СУБД при выборе плана, что приведет к катастрофическому
падению производительности запроса. В данном случае проблемой для оптимизатора
является выбор правильного способа соединения двух выборок данных в запросе. Выбор
алгоритма соединения зависит от того, сколько записей будет содержаться в одной и в
другой выборке. В случае соединения двух физических таблиц СУБД может легко
определить объем обеих выборок на основании имеющейся статистики. Если же одна из
соединяемых выборок представляет собой вложенный запрос, то понять, какое
количество записей она вернет, становится очень сложно.

Поэтому вместо вложенных запросов в соединениях ВСЕГДА нужно использовать
временные таблицы. При этом их необходимо проиндексировать по полям, участвующим
в условии соединения (листинг 4.14).

Листинг 4.14. Выполнение запроса для получения остатков номенклатуры, содержащихся в документе, – правильный
вариант


background image

В данном запросе вместо вложенного запроса в соединении используется временная
таблица СоставДокумента. Таким образом, СУБД сможет легко определить размер
каждой выборки, участвующей в соединении. Это позволит СУБД гарантированно
выбрать самый быстрый из всех возможных планов. Переписанный подобным образом
запрос будет работать одинаково хорошо и, главное, стабильно на любых СУБД, что
особенно важно при разработке тиражных решений.

Кроме того, список номенклатуры из временной таблицы ограничивает объем выборки в
виртуальной таблице остатков, что также делает запрос более эффективным.

И, наконец, приведенный запрос лучше читается, проще для понимания и отладки.

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


background image

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

Если в запросе выбираются данные из виртуальных таблиц, то при трансляции запроса в
язык SQL платформа сама обращается к итоговым таблицам регистров. В случаях, когда
часть информации получается из таблицы итогов, а часть – из таблицы движений
регистра, соединение с виртуальной таблицей на уровне SQL может быть реализовано
как соединение с подзапросом. В этом случае оптимизатор СУБД может точно так же
выбрать неоптимальный план, как при работе с подзапросом в явном виде (см.
предыдущий раздел).

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

Таким образом, листинг 4.14 из предыдущего раздела, в котором выполнялось
соединение с виртуальной таблицей остатков
РегистрНакопления.ТоварыНаСкладах.Остатки(), можно переписать следующим
образом (листинг 4.15).

Листинг 4.15. Выполнение запроса для получения остатков номенклатуры, содержащихся в документе, – правильный
вариант


background image

В данном запросе используется еще одна временная таблица ОстаткиТоваров, в
которую помещаются данные виртуальной таблицы остатков. Обратите внимание, что
объем выборки в виртуальной таблице остатков ограничивает список номенклатуры из
первой временной таблицы СоставДокумента. Затем в третьем запросе данные этих
двух временных таблиц связываются левым соединением. Данные временных таблиц
доступны в этом запросе, так как все три запроса используют один менеджер временных
таблиц.

Не использовать вложенные запросы в условиях соединения

По тем же причинам, по которым «вредно» использовать соединения с вложенными
запросами (раздел "

Соединения с вложенными запросами

"), также потенциально опасно и

использование вложенных запросов в условиях соединения ПО.

Исключить получение поля «Ссылка» через точку

Многие таблицы объектов конфигурации содержат поля, ссылающиеся на другие
таблицы. Например, реквизит Склад документа ПоступлениеТоваров имеет ссылочный


background image

тип на справочник Склады. Это значит, что в поле Склад таблицы документа содержатся
ссылки на конкретные элементы справочника складов.

Поэтому совершенно излишним является получение в запросе поля Ссылка через точку
от полей ссылочного типа. Например, требуется отобрать документы по значению
ссылочного поля Склад. В этом случае следующий вариант запроса будет
неоптимальным (листинг 4.16).

Листинг 4.16. Вывод документов «Поступление товаров» с отбором по складу – неправильный вариант

При выполнении запроса будет выполнено ненужное в данном случае соединение с
таблицей справочника Склады. Поэтому запрос нужно переписать следующим образом
(листинг 4.17).

Листинг 4.17. Вывод документов «Поступление товаров» с отбором по складу – правильный вариант

Этот вариант запроса оптимальнее, так как вся нужная информация уже есть в таблице
документа.

Ограничить получение данных через точку от полей составного ссылочного типа

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

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