Что означает ключевое слово ПО в запросах 1С и как работают соединения таблиц?

Программист IT и автоматизация бизнеса
← На главную

При изучении языка запросов 1С начинающие разработчики часто сталкиваются с оператором СОЕДИНЕНИЕ и ключевым словом ПО. Разберем подробно, для чего нужно это слово, какую логику оно выполняет под капотом СУБД и как правильно применять соединения таблиц на практике.

Назначение оператора ПО в языке запросов 1С

Ключевое слово ПО указывает условие, по которому строки из первой (левой) таблицы сопоставляются со строками из второй (правой) таблицы. Если выражение, указанное после ПО, принимает значение ИСТИНА, данные этих строк объединяются в одну строку и попадают в результирующую выборку.

Рассмотрим стандартный пример запроса:


ВЫБРАТЬ РАЗЛИЧНЫЕ
	ПереченьПоступлений.Товар КАК ПоступившийТовар,
	ПереченьПродаж.Товар КАК ПроданныйТовар
ИЗ
	Документ.ПоступлениеТоваров.ПереченьТоваров КАК ПереченьПоступлений
	СОЕДИНЕНИЕ Документ.ПродажаТоваров.ПереченьТоваров КАК ПереченьПродаж
	ПО ПереченьПоступлений.Товар = ПереченьПродаж.Товар

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

Логика работы соединений и вариант ПО ИСТИНА

Логику работы внутреннего соединения можно представить следующим образом: каждая строка первой таблицы «примеряется» к каждой строке второй таблицы. Если логическое выражение после ПО истинно, данные объединяются.

Что произойдет, если написать условие связи ПО ИСТИНА? Проанализируем эту ситуацию:


ВЫБРАТЬ
	Т1.Товар,
	Т2.Склад
ИЗ
	Таблица1 КАК Т1
	СОЕДИНЕНИЕ Таблица2 КАК Т2
	ПО ИСТИНА

При таком условии абсолютно каждая комбинация строк первой и второй таблиц дает ИСТИНА. В результате получится декартово произведение множеств: количество строк в итоговой выборке будет равно произведению (а не сумме) количества строк первой и второй таблиц. Также декартово произведение можно получить, просто перечислив таблицы через запятую в секции ИЗ (ИЗ Таблица1 КАК Т1, Таблица2 КАК Т2).

Разновидности соединений таблиц

Разберем основные типы соединений в запросах 1С:

  1. ВНУТРЕННЕЕ СОЕДИНЕНИЕ — в результат попадают только те строки, для которых условие связи в секции ПО вернуло значение ИСТИНА для обеих таблиц.
  2. ЛЕВОЕ СОЕДИНЕНИЕ — в результат обязательно попадают все строки из левой таблицы. Если для строки левой таблицы не нашлось совпадения в правой, поля правой таблицы заполняются значением NULL.
  3. ПРАВОЕ СОЕДИНЕНИЕ — работает аналогично левому, но гарантия сохранения всех строк действует для правой таблицы.
  4. ПОЛНОЕ СОЕДИНЕНИЕ — сочетает свойства левого и правого соединений: выводит все совпадающие строки, а также несовпавшие строки из обеих таблиц (с подстановкой NULL).

Важные нюансы и оптимизация соединений

Соединение таблиц — ресурсоемкая операция для базы данных. Рассмотрим ключевые правила оптимизации и особенности работы СУБД, которые важно учитывать при составлении запросов:

  1. Отличие условий в секциях ПО и ГДЕ при ЛЕВОМ СОЕДИНЕНИИ:

    Если условие отбора к правой таблице поместить в секцию ГДЕ, а не в ПО, запрос отфильтрует строки со значением NULL. В результате ЛЕВОЕ СОЕДИНЕНИЕ превратится во ВНУТРЕННЕЕ СОЕДИНЕНИЕ. Все дополнительные условия для правой таблицы нужно писать непосредственно в секции ПО через оператор И.

  2. Использование временных таблиц и индексов:

    При необходимости соединить сложный подзапрос с физической таблицей СУБД не всегда может построить оптимальный план выполнения, так как у подзапроса нет индексов. Эффективным решением является выгрузка данных во временную таблицу (ПОМЕСТИТЬ ИмяВременнойТаблицы), индексация ключевых полей через ИНДЕКСИРОВАТЬ ПО и последующее соединение с полученной временной таблицей.

  3. Сравнение полей составного типа:

    Если поле связи имеет составной тип данных (например, Регистратор), платформа 1С автоматически генерирует скрытые соединения со всеми таблицами входящих типов. Для предотвращения падения производительности следует ограничивать тип с помощью функции ВЫРАЗИТЬ(Таблица.Реквизит КАК Тип).

  4. Неявные соединения через точку:

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

  5. Особенности сравнения со значениями NULL:

    В SQL выражение NULL = NULL не дает истины. Если ключевые поля двух таблиц содержат пустые значения NULL, они не соединятся по равенству =. При необходимости связывания таких строк следует использовать функцию ЕСТЬNULL().

← На главную