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

В этой статье мы разберём не только синтаксис левого соединения в языке запросов 1С, но и покажем, как оно применяется на практике — от простых примеров до сложных сценариев с несколькими таблицами. Вы узнаете, чем LEFT JOIN отличается от INNER JOIN и RIGHT JOIN, как избежать типичных ошибок при его использовании, и почему иногда результаты запроса могут показаться неожиданными. А для тех, кто только начинает осваивать запросы в 1С, мы подготовили пошаговые инструкции с разбором кода.

Важно: статья ориентирована на актуальные версии платформы 1С:Предприятие 8.3 (включая последние релизы). Если вы работаете с устаревшими конфигурациями (например, 7.7), некоторые примеры могут потребовать адаптации.

Что такое левое соединение и зачем оно нужно

Левое соединение (LEFT JOIN) — это тип объединения таблиц в запросах, при котором в результат попадают все записи из левой таблицы, а данные из правой добавляются только при наличии совпадений по условию. Если совпадений нет, поля правой таблицы заполняются значением NULL (или эквивалентным пустым значением в 1С).

Основное преимущество такого подхода — сохранение целостности данных левой таблицы, что критично для отчётов, где важно показать все элементы справочника (например, номенклатуру), даже если по ним не было движений (например, продаж). Без левого соединения такие записи просто «пропадали» бы из результата.

  • 📌 Пример 1: Вывести все товары из справочника Номенклатура, включая те, по которым не было продаж за месяц.
  • 📌 Пример 2: Показать всех контрагентов с указанием их последнего заказа (даже если заказов не было).
  • 📌 Пример 3: Сформировать список сотрудников с данными об их премиях (включая тех, кто премий не получал).

В отличие от внутреннего соединения (INNER JOIN), которое возвращает только пересекающиеся данные, левое соединение гарантирует, что ни одна запись из левой таблицы не будет утеряна. Это делает его незаменимым инструментом для аналитических задач, где важна полнота информации.

📊 Как часто вы используете LEFT JOIN в запросах 1С?
Постоянно, в большинстве запросов
Иногда, для специфических задач
Рядом не стоял, только INNER JOIN
Что это?

Синтаксис левого соединения в 1С

В языке запросов 1С левое соединение задаётся с помощью конструкции ЛЕВОЕ СОЕДИНЕНИЕ (или LEFT JOIN в англоязычном синтаксисе). Общий вид запроса:

ВЫБРАТЬ

Таблица1.Поле1,

Таблица1.Поле2,

Таблица2.Поле1 КАК ПолеИзТаблицы2

ИЗ

Таблица1 КАК Таблица1

ЛЕВОЕ СОЕДИНЕНИЕ Таблица2 КАК Таблица2

ПО Таблица1.Ключ = Таблица2.Ключ

Где:

  • 🔹 Таблица1 — «левая» таблица, записи которой будут включены в результат полностью.
  • 🔹 Таблица2 — «правая» таблица, данные из которой добавляются только при совпадении.
  • 🔹 ПО Таблица1.Ключ = Таблица2.Ключ — условие соединения (обычно по полю-ссылке или уникальному идентификатору).

Важно: если в правой таблице нет совпадающих записей, поля из неё будут содержать NULL. В 1С это проявляется как пустые значения или Неопределён для ссылочных типов.

💡

Чтобы проверить, какие записи не имеют совпадений в правой таблице, добавьте в запрос условие ГДЕ Таблица2.Ключ ЕСТЬ NULL. Это поможет выявить «сиротские» данные.

Отличия LEFT JOIN от других типов соединений

В 1С поддерживаются несколько типов соединений, и выбор правильного зависит от задачи. Рассмотрим ключевые различия:

Тип соединения Синтаксис в 1С Что возвращает Когда использовать
Левое (LEFT JOIN) ЛЕВОЕ СОЕДИНЕНИЕ Все записи из левой таблицы + совпадающие из правой (или NULL) Когда нужны все записи из основной таблицы, даже без связей
Внутреннее (INNER JOIN) СОЕДИНЕНИЕ (по умолчанию) Только записи, есть совпадения в обеих таблицах Когда нужны только пересекающиеся данные
Правое (RIGHT JOIN) ПРАВОЕ СОЕДИНЕНИЕ Все записи из правой таблицы + совпадающие из левой (или NULL) Редко используется, можно заменить LEFT JOIN с перестановкой таблиц
Полное (FULL JOIN) Нет прямой поддержки, эмулируется через ОБЪЕДИНИТЬ Все записи из обеих таблиц (с NULL для несовпадений) Для аналитики, когда важны данные из обеих таблиц

На практике LEFT JOIN используется чаще всего, так как он позволяет сохранять контроль над основной таблицей. Например, при формировании отчёта по остаткам товаров на складе вы хотите видеть всю номенклатуру, а не только ту, по которой были движения.

⚠️ Внимание: В некоторых СУБД (например, PostgreSQL или MS SQL) левое соединение может работать быстрее, чем полное объединение, но в 1С оптимизатор запросов не всегда учитывает это. Для больших таблиц тестируйте производительность!

Практические примеры левого соединения в 1С

Рассмотрим реальные сценарии, где LEFT JOIN незаменим. Все примеры приведены для типовой конфигурации 1С:Управление торговлей 11, но легко адаптируются под другие решения.

Пример 1: Товары с остатками и без

Задача: вывести список всей номенклатуры с указанием текущего остатка на складе. Если остатка нет — показать 0.

ВЫБРАТЬ

Номенклатура.Наименование КАК Товар,

ЕСТЬNULL(ОстаткиТоваров.Количество, 0) КАК Остаток

ИЗ

Справочник.Номенклатура КАК Номенклатура

ЛЕВОЕ СОЕДИНЕНИЕ РегистрНакопления.ОстаткиТоваров.Остатки(

&ДатаОстатков,

Склад = &ТекущийСклад

) КАК ОстаткиТоваров

ПО Номенклатура.Ссылка = ОстаткиТоваров.Номенклатура

Здесь ЕСТЬNULL заменяет NULL на 0 для удобства отображения. Параметры &ДатаОстатков и &ТекущийСклад передаются извне.

Пример 2: Контрагенты с последними заказами

Задача: показать всех контрагентов и дату их последнего заказа (если заказов не было — оставить пустым).

ВЫБРАТЬ

Контрагенты.Наименование КАК Клиент,

МАКСИМУМ(Заказы.Дата) КАК ПоследнийЗаказ

ИЗ

Справочник.Контрагенты КАК Контрагенты

ЛЕВОЕ СОЕДИНЕНИЕ Документ.ЗаказПокупателя КАК Заказы

ПО Контрагенты.Ссылка = Заказы.Контрагент

ГРУППИРОВКА ПО

Контрагенты.Ссылка,

Контрагенты.Наименование

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

Пример 3: Сотрудники и их премиальные

Задача: сформировать список сотрудников с суммой премий за квартал, включая тех, кто премий не получал.

ВЫБРАТЬ

Сотрудники.Наименование КАК ФИО,

ЕСТЬNULL(СУММА(Премии.Сумма), 0) КАК СуммаПремий

ИЗ

Справочник.Сотрудники КАК Сотрудники

ЛЕВОЕ СОЕДИНЕНИЕ Документ.ПремияСотрудникам КАК Премии

ПО Сотрудники.Ссылка = Премии.Сотрудник

И Премии.Дата МЕЖДУ &НачалоКвартала И &КонецКвартала

ГРУППИРОВКА ПО

Сотрудники.Ссылка,

Сотрудники.Наименование

⚠️ Внимание: При использовании LEFT JOIN с виртуальными таблицами регистров (например, ОстаткиТоваров.Остатки()) убедитесь, что параметры виртуальной таблицы (дата, измерения) переданы корректно. Иначе запрос может вернуть неполные данные.

Типичные ошибки при использовании LEFT JOIN

Даже опытные разработчики иногда сталкиваются с неожиданными результатами при работе с левыми соединениями. Вот наиболее распространённые ошибки и как их избежать:

  1. 🔴 Условия в WHERE, убивающие левое соединение

    Если вы добавляете условие по полю из правой таблицы в секцию ГДЕ, левое соединение фактически превращается во внутреннее. Например:

    ЛЕВОЕ СОЕДИНЕНИЕ Заказы ПО ...
    

    ГДЕ Заказы.Дата > &ДатаНачала

    Решение: переносите такие условия в секцию ПО или используйте подзапросы.

  2. 🔴 Игнорирование NULL-значений

    Поля из правой таблицы могут содержать NULL, что приведёт к ошибкам при агрегации (например, СУММА проигнорирует такие строки). Всегда используйте ЕСТЬNULL или ВЫРАЗИТЬ.

  3. 🔴 Неправильное направление соединения

    Если перепутать левую и правую таблицы, результат будет неверным. Например, соединение справочника с документом как правой таблицей даст только тех контрагентов, у которых есть заказы.

Почему запрос с LEFT JOIN работает медленно?

Левое соединение может тормозить, если:

1. В правой таблице нет индексов по полю соединения.

2. Условие соединения слишком сложное (например, включает функции или вычисления).

3. Виртуальная таблица регистра не оптимизирована (например, слишком широкий временной диапазон).

Для ускорения:

- Проверьте план выполнения запроса в консоли запросов 1С.

- Добавьте индексы на поля соединения.

- Разбейте сложный запрос на несколько простых с временными таблицами.

Оптимизация запросов с LEFT JOIN в 1С

Левое соединение может замедлять выполнение запросов, особенно если правая таблица содержит миллионы записей. Вот несколько способов оптимизации:

  • Индексируйте поля соединения. Убедитесь, что поля, по которым происходит соединение, проиндексированы в базе данных. В 1С индексы создаются автоматически для ссылочных полей, но для пользовательских реквизитов может потребоваться ручная настройка.
  • Ограничивайте данные в правой таблице. Если возможно, добавьте условия фильтрации непосредственно в секцию ПО или используйте подзапросы для предварительной выборки:
ЛЕВОЕ СОЕДИНЕНИЕ (

ВЫБРАТЬ

Заказы.Контрагент,

Заказы.Дата

ИЗ

Документ.ЗаказПокупателя КАК Заказы

ГДЕ

Заказы.Дата > &ДатаНачала

) КАК ФильтрованныеЗаказы ПО ...

  • Избегайте соединений с виртуальными таблицами больших регистров. Если вам нужны остатки только по определённому складу или номенклатуре, передавайте эти параметры в виртуальную таблицу:
ОстаткиТоваров.Остатки(&Дата, Склад = &ТекущийСклад, Номенклатура В (&СписокТоваров))
  • Используйте временные таблицы. Для сложных отчётов разбейте запрос на части, сохраняя промежуточные результаты во временные таблицы.
💡

Левое соединение — мощный инструмент, но его следует использовать осознанно. Если вам нужны только пересекающиеся данные, внутреннее соединение (INNER JOIN) будет работать быстрее.

Когда левое соединение не нужно

Несмотря на универсальность, LEFT JOIN не всегда оправдан. Вот случаи, когда лучше использовать другие подходы:

  1. 📉 Вам нужны только совпадающие записи.

    Если задача — найти пересечение данных (например, товары, которые продавались в определённом регионе), внутреннее соединение (INNER JOIN) будет проще и быстрее.

  2. 📉 Правая таблица содержит дубликаты.

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

  3. 📉 Вы работаете с агрегатными функциями по правой таблице.

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

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

FAQ: Частые вопросы о LEFT JOIN в 1С

Можно ли в 1С использовать несколько LEFT JOIN в одном запросе?

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

ВЫБРАТЬ ...

ИЗ Таблица1 КАК Т1

ЛЕВОЕ СОЕДИНЕНИЕ Таблица2 КАК Т2 ПО Т1.Ключ = Т2.Ключ

ЛЕВОЕ СОЕДИНЕНИЕ Таблица3 КАК Т3 ПО Т2.Ключ = Т3.Ключ

При этом Таблица3 будет «правой» относительно Таблица2, но «левой» относительно потенциальной Таблица4.

Почему в результате запроса с LEFT JOIN появляются повторяющиеся строки?

Это происходит, если в правой таблице есть несколько записей, соответствующих одной строке из левой таблицы. Например, у одного контрагента может быть несколько заказов. Чтобы избежать дублирования:

  • Используйте агрегатные функции (МАКСИМУМ, МИНИМУМ) для сводки данных.
  • Добавьте ГРУППИРОВКА ПО полям из левой таблицы.
  • Используйте подзапросы для предварительной агрегации данных в правой таблице.
Как эмулировать FULL JOIN в 1С, если его нет в синтаксисе?

Полное соединение (FULL JOIN) можно эмулировать с помощью объединения результатов левого и правого соединений:

ВЫБРАТЬ ... ИЗ Таблица1 ЛЕВОЕ СОЕДИНЕНИЕ Таблица2 ПО ...

ОБЪЕДИНИТЬ

ВЫБРАТЬ ... ИЗ Таблица2 ЛЕВОЕ СОЕДИНЕНИЕ Таблица1 ПО ...

ГДЕ Таблица1.Ключ ЕСТЬ NULL

Это вернёт все записи из обеих таблиц, заполняя NULL для несовпадающих строк.

Влияет ли LEFT JOIN на производительность отчётов в 1С?

Да, левое соединение может значительно замедлить выполнение отчётов, особенно если:

  • Правая таблица содержит миллионы записей.
  • Условие соединения не оптимизировано (например, включает функции или вычисления).
  • Запрос не использует индексы.

Для ускорения:

  • Ограничивайте данные в правой таблице с помощью условий в секции ПО.
  • Используйте временные таблицы для промежуточных результатов.
  • Проверяйте план выполнения запроса в консоли 1С.
Можно ли использовать LEFT JOIN с виртуальными таблицами регистров?

Да, левое соединение часто применяется с виртуальными таблицами регистров накопления (например, ОстаткиТоваров.Остатки() или Продажи.Обороты()). Главное — правильно передавать параметры виртуальной таблицы (дата, измерения) и учитывать, что:

  • Если в виртуальной таблице нет данных по ключу, поля будут содержать NULL.
  • Для регистров с большим объёмом данных виртуальные таблицы могут тормозить — в таких случаях используйте отбор по конкретным измерениям.

Пример:

ЛЕВОЕ СОЕДИНЕНИЕ РегистрНакопления.Продажи.Обороты(

&НачалоПериода,

&КонецПериода,

,

Номенклатура В (&СписокТоваров)

) КАК Продажи ПО Номенклатура.Ссылка = Продажи.Номенклатура