К статье
Практический материал

Разработка и Конфигурация · 10 мин

Конструкция ВЫБОР КОГДА ТОГДА КОНЕЦ в запросах 1С

Как работает конструкция ВЫБОР КОГДА ТОГДА КОНЕЦ в языке запросов 1С: синтаксис, примеры, типовые ошибки, сравнение с ЕСТЬNULL и проверка результата.

Конструкция ВЫБОР КОГДА ТОГДА КОНЕЦ — это аналог оператора CASE в SQL, встроенный в язык запросов 1С. Она позволяет вернуть разные значения в зависимости от условий прямо в тексте запроса, без построчной обработки результата в коде. Это один из самых востребованных приёмов при построении отчётов, динамических списков и СКД, где нужно классифицировать данные: подставить текстовый статус вместо ссылки, разбить суммы по категориям, заменить пустые значения.

Механизм прост: запрос проверяет условия КОГДА сверху вниз и возвращает значение первого выполнившегося ТОГДА. Если ни одно условие не сработало, возвращается значение из ИНАЧЕ, а при его отсутствии — NULL. Завершается конструкция обязательным словом КОНЕЦ. Ошибки в этой логике — пропущенный КОНЕЦ, несовместимые типы значений, забытое ИНАЧЕ — приводят либо к синтаксической ошибке, либо к неочевидным NULL в отчёте.

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

Синтаксис конструкции ВЫБОР КОГДА ТОГДА КОНЕЦ

Полная форма записи выглядит так:

ВЫБОР

КОГДА <Условие1> ТОГДА <Значение1>

КОГДА <Условие2> ТОГДА <Значение2>

ИНАЧЕ <ЗначениеПоУмолчанию>

КОНЕЦ

Условий КОГДА может быть сколько угодно, но каждое должно быть логическим выражением: сравнение, ЕСТЬ NULL, В, ПОДОБНО и другие предикаты языка запросов. Значения после ТОГДА и ИНАЧЕ должны быть совместимы по типу — иначе запрос вернёт значение неопределённого типа, что создаст проблемы при группировке и выводе в СКД.

Ключевые правила, которые нужно держать в голове:

  • условия проверяются строго сверху вниз, поэтому более частные условия ставят выше общих;
  • слово КОНЕЦ обязательно — без него конструктор запроса выдаст синтаксическую ошибку;
  • ИНАЧЕ не обязательно, но без него несработавшие строки получат NULL;
  • конструкцию можно вкладывать друг в друга, но глубокая вложенность ухудшает читаемость и производительность.

Простой пример: подстановка статуса вместо ссылки

Типовая задача — вывести в отчёте понятный текст вместо технического значения перечисления или булева поля. Например, нужно показать признак проведения документа словами:

ВЫБРАТЬ

Реализация.Номер,

ВЫБОР

КОГДА Реализация.Проведен ТОГДА "Проведён"

КОГДА Реализация.ПометкаУдаления ТОГДА "Помечен на удаление"

ИНАЧЕ "Черновик"

КОНЕЦ КАК Состояние

ИЗ

Документ.РеализацияТоваровУслуг КАК Реализация

Обратите внимание на порядок условий: помеченный на удаление документ может быть одновременно проведённым, и если поменять условия местами, такой документ попадёт в «Проведён». Сначала проверяйте более специфичные состояния.

Псевдоним КАК Состояние после КОНЕЦ обязателен, если поле будет использоваться в группировке, упорядочивании или настройках СКД — без имени обратиться к вычисляемому полю нельзя.

Классификация по диапазонам значений

Вторая частая задача — разбить числовые значения на категории: ABC-анализ, группировка по сумме долга, возрастные интервалы. Здесь условия строятся на сравнениях:

ВЫБОР

КОГДА Продажи.Сумма >= 100000 ТОГДА "Крупная"

КОГДА Продажи.Сумма >= 10000 ТОГДА "Средняя"

ИНАЧЕ "Мелкая"

КОНЕЦ КАК КатегорияСделки

Поскольку проверка идёт сверху вниз, верхняя граница проверяется первой, и дополнительное условие «меньше 100000» во второй строке не требуется — туда попадут только суммы, не прошедшие первую проверку. Это удобно, но требует аккуратности: если случайно поставить условие >= 10000 первым, категория «Крупная» никогда не будет заполнена, и ошибка визуально не проявится как сбой запроса.

ВЫБОР в сочетании с ЕСТЬNULL и обработка пустых значений

Частая ошибка — сравнивать поле со значением, когда оно может содержать NULL, например после левого соединения. Сравнение Поле = 0 для NULL не выполнится, и строка уйдёт в ветку ИНАЧЕ. Правильно сначала устранить NULL:

ВЫБОР

КОГДА ЕСТЬNULL(Остатки.Количество, 0) > 0 ТОГДА "В наличии"

ИНАЧЕ "Нет на складе"

КОНЕЦ КАК НаличиеТовара

Альтернатива — проверка через предикат ЕСТЬ NULL:

ВЫБОР

КОГДА Остатки.Количество ЕСТЬ NULL ТОГДА "Нет данных"

КОГДА Остатки.Количество > 0 ТОГДА "В наличии"

ИНАЧЕ "Нет на складе"

КОНЕЦ

Сравнение вариантов

ЕСТЬNULL(Поле, 0) внутри условия

Короткая запись, подходит когда NULL логически равен значению по умолчанию; не позволяет отличить NULL от реального нуля

Проверка ЕСТЬ NULL отдельным КОГДА

Даёт отдельную ветку для отсутствующих данных; запись длиннее, но аналитически точнее

Только ИНАЧЕ без обработки NULL

Простейший вариант, но NULL неявно попадает в ветку по умолчанию — легко пропустить потерю строк при соединении

ВЫБОР в итогах, группировках и СКД

Конструкция работает не только в списке полей, но и внутри агрегатных функций. Классический приём — сводный отчёт, где одну колонку «разворачивают» в несколько:

СУММА(ВЫБОР

КОГДА Продажи.Склад = &ОсновнойСклад ТОГДА Продажи.Сумма

ИНАЧЕ 0

КОНЕЦ) КАК СуммаОсновнойСклад

Здесь ИНАЧЕ 0 обязательно: без него несработавшие строки дадут NULL, и хотя СУММА игнорирует NULL, в некоторых сценариях (например, при делении или сравнении итога) это приведёт к неожиданным пустотам. Тип значения в ветках должен совпадать — число с числом, строка со строкой.

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

Типичные ошибки и как их найти

Большинство проблем с конструкцией делится на четыре группы. Первая — синтаксические: пропущенный КОНЕЦ, лишняя запятая перед КОНЕЦ, пропущенное ТОГДА. Их конструктор запросов отлавливает сразу. Вторая группа опаснее — логические ошибки, которые не вызывают сообщений об ошибке: неверный порядок условий, забытое ИНАЧЕ, сравнение с NULL через равенство.

Третья группа — типизация: в одной ветке строка фиксированной длины, в другой неограниченная строка, в итоге поле обрезается или не участвует в группировке. Четвёртая — производительность: сложный многоуровневый ВЫБОР в условии соединения или отбора заставляет СУБД вычислять выражение для каждой строки без использования индексов.

Типичные ошибки
01
Пропущено ИНАЧЕ — строки вне условий получают NULL и исчезают из группировок отчёта
02
Общее условие стоит выше частного — частная ветка никогда не срабатывает, ошибка не видна без проверки данных
03
Сравнение с NULL через равенство после левого соединения — условие не выполняется, строки уходят в ИНАЧЕ
04
Разные типы значений в ТОГДА и ИНАЧЕ — поле становится составным, ломаются итоги и настройки СКД
05
ВЫБОР в условии соединения таблиц — резкое падение производительности на больших объёмах

Как проверить результат запроса

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

Контрольные точки

Как проверить результат

Значения вычисляемого поля
Норма

Все строки заполнены ожидаемыми значениями из веток ТОГДА/ИНАЧЕ

Тревожный признак

Встречаются пустые значения (NULL) — значит, не хватает ИНАЧЕ или условие не сработало

Граничные значения диапазонов
Норма

Значение ровно на границе попадает в задуманную категорию

Тревожный признак

Граничное значение ушло не в ту ветку — перепутан порядок КОГДА или знак сравнения

Итоги по сгруппированному полю
Норма

Суммы и количества совпадают с контрольным расчётом без ВЫБОР

Тревожный признак

Итоги расходятся — часть строк потеряна из-за NULL или неверной классификации

Порядок действий при написании конструкции
  1. 1
    Определите полный список условий и упорядочьте их от частного к общему
  2. 2
    Запишите ветки КОГДА...ТОГДА, следя за одинаковым типом возвращаемых значений
  3. 3
    Добавьте ИНАЧЕ со значением по умолчанию и завершите конструкцию словом КОНЕЦ
  4. 4
    Назначьте полю псевдоним через КАК
  5. 5
    Выполните запрос в консоли и проверьте граничные значения и отсутствие NULL

FAQ по конструкции ВЫБОР КОГДА ТОГДА КОНЕЦ

Обязательно ли писать ИНАЧЕ?

Нет, синтаксис этого не требует. Но без ИНАЧЕ все строки, не попавшие ни в одно условие, получат NULL. В отчётах это проявляется как пустые ячейки и потерянные строки в группировках, поэтому на практике ИНАЧЕ стоит добавлять всегда.

Можно ли использовать ВЫБОР в секции ГДЕ?

Да, конструкция допустима в условиях отбора, соединения и в предложении ИМЕЮЩИЕ. Однако в условиях соединения и отбора она обычно отключает использование индексов, что на больших таблицах заметно замедляет запрос. Часто проще переписать условие через ИЛИ или параметры.

Чем ВЫБОР отличается от ЕСТЬNULL?

ЕСТЬNULL — частный случай: подставляет значение вместо NULL. ВЫБОР — универсальный условный оператор с произвольными условиями. Если нужно только заменить NULL, ЕСТЬNULL короче и читаемее; для любой другой логики используйте ВЫБОР.

Можно ли вкладывать ВЫБОР внутрь ВЫБОР?

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

Почему поле с ВЫБОР не группируется в отчёте СКД?

Чаще всего причина в смешении типов значений в ветках ТОГДА и ИНАЧЕ — поле получает составной тип. Приведите все ветки к одному типу (например, через ВЫРАЗИТЬ) и убедитесь, что полю назначен псевдоним.

Как сравнить поле с перечислением в условии КОГДА?

Через значение предопределённого элемента: КОГДА Документ.ВидОперации = ЗНАЧЕНИЕ(Перечисление.ВидыОпераций.Продажа) ТОГДА ... — имя перечисления и элемента должны точно совпадать с метаданными конфигурации.

Итог

Что важно запомнить

ВЫБОР КОГДА ТОГДА КОНЕЦ проверяет условия сверху вниз и возвращает значение первой сработавшей ветки. Ставьте частные условия выше общих, всегда добавляйте ИНАЧЕ, держите одинаковый тип значений во всех ветках и проверяйте результат на граничных значениях и NULL.