Итак допустим мы пишем в 1С в консоли запросов:
ВЫБРАТЬ
Товары.Ссылка,
Товары.Поставщик.Наименование
ИЗ
Справочник.Товары КАК Товары
В запросе к sql серверу он будет выглядеть так:
SELECT
T1._IDRRef,
T2._Description
FROM _Reference7 T1
LEFT OUTER JOIN _Reference8 T2
ON T1._Fld109RRef = T2._IDRRef
Как видим появилось левое соединение с таблицей поставщиков. А вот если бы Товары.Поставщик мог ссылаться не только на один справочник, а на несколько, то таких соединений было бы несколько - столько же на сколько таблиц может ссылаться этот реквизит.
Вроде бы всё ясно. Но глядя в логи PgSQL мы видим что от 1С пришёл не один запрос, а ещё несколько, попроще:
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\362'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\363'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\364'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\365'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\366'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\215\\004=q\\000w'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\241\\000\\015\\210C\\315\\033\\021\\334\\216\\251-\\227\\247I'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\241\\000\\015\\210C\\315\\033\\021\\334\\216\\254\\324q\\326\\307'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\241\\000\\015\\210C\\315\\033\\021\\334\\216\\263`\\367\\013M'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\242\\000\\015\\210C\\315\\033\\021\\334\\221\\003\\235\\177\\321\\013'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\242\\000\\015\\210C\\315\\033\\021\\334\\221\\016Q\\000\\330\\200'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\242\\000\\015\\210C\\315\\033\\021\\334\\221\\021\\361ix.'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\215:\\000\\015\\210C\\315\\033\\021\\3352\\033\\247\\243\\012\\256'::bytea
;
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\215:\\000\\015\\210C\\315\\033\\021\\3352\\033\\247\\243\\012\\257'::bytea
Что это за запросы? Хе! Это запросы на получение представления ссылки в результатах, отображаемых на экране.
Пробуем оптимизировать наш запрос. Попробуем получить представление и посмотрим сумеет ли 1С понять что оно уже получено и повторно его получать ненадо.
ВЫБРАТЬ
Товары.Ссылка,
Товары.Наименование,
Товары.Представление,
Товары.Поставщик.Наименование
ИЗ
Справочник.Товары КАК Товары
В PostgreSQL пойдёт такой запрос:
SELECT
T1._IDRRef,
T1._Description,
T1._IDRRef,
T1._Description,
T2._Description
FROM _Reference7 T1
LEFT OUTER JOIN _Reference8 T2
ON T1._Fld109RRef = T2._IDRRef
но тут же в логах мы видим ещё 15 простых запросов вида
SELECT
T1._IDRRef,
T1._Description
FROM _Reference7 T1
WHERE T1._IDRRef = '\\214\\240\\000\\015\\210C\\315\\033\\021\\334\\214\\376\\314j}\\362'::bytea
Посчитав число отображаемых строк мы убеждаемся, что 1С не сопоставила ссылку и представление. Это вобщем логично, поскольку отображаемая таблица значений не связана с данными и поэтому 1С вынуждена подтягивать представление ссылки по мере отображения на экране.
Однако есть способ заставить 1С делать только один запрос. Для этого перепишем его вот так:
ВЫБРАТЬ
Товары.Представление,
Товары.Поставщик.Наименование
ИЗ
Справочник.Товары КАК Товары
Упорядочить по
Товары.Представление // Хочется, всё-такивидеть упорядоченные товары
При этом в Postgre отправится такой запрос
SELECT
T1._IDRRef,
T1._Description,
T2._Description
FROM _Reference7 T1
LEFT OUTER JOIN _Reference8 T2
ON T1._Fld109RRef = T2._IDRRef
ORDER BY (T1._IDRRef), (T1._Description)
Запрос ушёл один, его результат отобразился без лишних обращений к базе.
Счастье? Нет!
И вот почему:
1. Несмотря на то что мы сказали "Упорядочить по Товары.Представление" произойдёт упорядочивание по внутренним идентификаторам.
2. Представление получает из базы и идентификатор и наименование, но это не даёт нам никаких преимуществ по сравнению с простой выборкой наименований поскольку идентификатор не доступен разработчику конфигурации. Из языка 1С доступно только текстовое описание.
По сути запрос к Представлению даёт меньше чем к наименованию.
ВЫБРАТЬ
Товары.Наименование,
Товары.Поставщик.Наименование
ИЗ
Справочник.Товары КАК Товары
Упорядочить по
Товары.Наименование
В PgSQL
SELECT
T1._Description,
T2._Description
FROM _Reference7 T1
LEFT OUTER JOIN _Reference8 T2
ON T1._Fld109RRef = T2._IDRRef
ORDER BY (T1._Description)
Эта статья навеяна двумя статьями //infostart.ru/public/61624 и //infostart.ru/public/61933 .