Отчеты и Аналитика · 10 мин
СКД в 1С: конструкция ВЫБОР КОГДА ТОГДА ИНАЧЕ
Как использовать конструкцию ВЫБОР КОГДА ТОГДА ИНАЧЕ в СКД 1С: синтаксис в запросе, вычисляемые поля, ресурсы, типичные ошибки и примеры настройки отчётов.
Конструкция ВЫБОР КОГДА ТОГДА ИНАЧЕ — аналог оператора «Если…Тогда…Иначе» в языке запросов 1С, и в системе компоновки данных (СКД) она применяется повсеместно: в тексте запроса набора данных, в вычисляемых полях, в ресурсах, в условном оформлении. С её помощью отчёт получает разные значения в зависимости от условий — например, подставляет «Просрочен» или «В норме» по дате оплаты, пересчитывает суммы по типу документа или заменяет NULL нулём.
Главная сложность для начинающих — понять, где именно писать условие: в запросе, в вычисляемом поле или в ресурсе, потому что синтаксис и поведение отличаются. Ошибка выбора места приводит к неверным итогам, пустым колонкам или падению производительности отчёта.
Ниже разобраны все варианты применения ВЫБОР в СКД: синтаксис, примеры, ограничения, проверка результата и типичные ошибки.
Где в СКД можно использовать ВЫБОР
Конструкция выбора доступна в четырёх местах схемы компоновки данных, и каждое имеет своё назначение:
- Текст запроса набора данных — полный синтаксис языка запросов: ВЫБОР КОГДА … ТОГДА … ИНАЧЕ … КОНЕЦ. Условие вычисляется на сервере СУБД, это самый быстрый вариант.
- Вычисляемые поля (закладка «Вычисляемые поля») — выражение на языке выражений СКД. Здесь нет оператора ВЫБОР, вместо него функция Выбор(условие, значение1, значение2).
- Ресурсы — выражение агрегирования, где ВЫБОР комбинируется с Сумма(), Максимум() и другими функциями для условных итогов.
- Условное оформление — там ВЫБОР не пишется, условие задаётся отбором, но логика «когда — тогда» реализуется через настройку оформления по условию.
Синтаксис ВЫБОР в запросе набора данных
Полная форма оператора в тексте запроса выглядит так:
ВЫБОР
КОГДА Продажи.Сумма > 100000
ТОГДА "Крупная"
КОГДА Продажи.Сумма > 10000
ТОГДА "Средняя"
ИНАЧЕ "Мелкая"
КОНЕЦ КАК КатегорияСделки
Правила, которые нужно соблюдать:
- Условий КОГДА может быть сколько угодно, они проверяются сверху вниз, срабатывает первое истинное.
- Ветка ИНАЧЕ формально необязательна, но без неё при невыполнении всех условий вернётся NULL — это частый источник пустых колонок и ошибок сравнения.
- Все ветки ТОГДА и ИНАЧЕ должны возвращать совместимые типы. Смешение строки и числа приведёт к ошибке или неявному приведению.
- Есть сокращённая форма для проверки на NULL: ВЫБОР КОГДА Поле ЕСТЬ NULL ТОГДА 0 ИНАЧЕ Поле КОНЕЦ, но для этой задачи лучше подходит функция ЕСТЬNULL(Поле, 0).
Практический пример — статус задолженности по дате оплаты:
ВЫБОР
КОГДА Взаиморасчеты.СуммаОстаток <= 0
ТОГДА "Оплачено"
КОГДА Взаиморасчеты.ДатаОплаты < &ТекущаяДата
ТОГДА "Просрочено"
ИНАЧЕ "В срок"
КОНЕЦ КАК СтатусОплаты
ВЫБОР в вычисляемых полях
Вычисляемые поля считаются уже после выполнения запроса, на уровне СКД, поэтому синтаксис другой — это язык выражений компоновки. Оператора ВЫБОР здесь нет, используется функция:
Выбор(Сумма > 100000, "Крупная", "Обычная")
Функция принимает три аргумента: условие, значение при истине, значение при лжи. Вложенные условия строятся вложением функций:
Выбор(Сумма > 100000, "Крупная",
Выбор(Сумма > 10000, "Средняя", "Мелкая"))
Когда выносить логику в вычисляемое поле, а когда оставлять в запросе? Если условие можно вычислить на уровне СУБД — делайте это в запросе: так быстрее и поле можно использовать в отборах и группировках запроса. Вычисляемое поле оправдано, когда нужны функции языка выражений СКД, которых нет в запросе, или когда условие зависит от уже вычисленных значений.
Условные ресурсы: ВЫБОР внутри агрегатных функций
Классическая задача — посчитать в одном отчёте отдельно суммы по условию, например план и факт или дебет и кредит в разных колонках. Для этого ВЫБОР помещается внутрь агрегатной функции ресурса:
Сумма(Выбор(ВидПоказателя = "План", Сумма, 0))
Или в полном синтаксисе запроса, если ресурс определяется в выражении:
Сумма(ВЫБОР КОГДА ВидДвижения = ЗНАЧЕНИЕ(ВидДвиженияНакопления.Приход)
ТОГДА Количество ИНАЧЕ 0 КОНЕЦ)
Такой приём позволяет получить «развёрнутые» колонки без соединений таблицы самой с собой. Важно: в ветке ИНАЧЕ для суммируемых ресурсов ставьте 0, а не NULL — сумма с NULL в отдельных строках может дать неожиданный результат при группировках.
Если в ресурсе с ВЫБОР итог по группе выходит пустым, хотя детальные строки заполнены, проверьте, что выражение ресурса рассчитывается на нужных группировках: в настройках ресурса есть колонка «Рассчитывать по», и по умолчанию ресурс может не выводиться на всех уровнях.
Сравнение вариантов размещения условия
| Место | Синтаксис | Когда применять | Ограничение |
|---|---|---|---|
| Запрос набора данных | ВЫБОР КОГДА … КОНЕЦ | Условие по полям таблиц, нужен отбор/группировка по результату | Только функции языка запросов |
| Вычисляемое поле | Выбор(усл., зн1, зн2) | Нужны функции СКД, условие над готовыми полями | Медленнее, нет отбора на уровне СУБД |
| Ресурс | Сумма(Выбор(...)) | Условные итоги в отдельных колонках | Работает только внутри агрегатов |
| Условное оформление | Отбор + оформление | Раскрасить строки по условию | Меняет только внешний вид, не значения |
Что выбрать
Оптимально для большинства задач: быстро, поле доступно для отборов и группировок. Ограничение — только возможности языка запросов.
Подходит, когда нужны функции языка выражений СКД или условие зависит от параметров отчёта. Не используйте для фильтрации миллионов строк.
Единственный способ получить условные итоги в отдельных колонках без усложнения запроса.
Типичные ошибки и как их избежать
Первая и самая частая ошибка — отсутствие ветки ИНАЧЕ. Если ни одно условие не сработало, поле получает NULL, и дальше это значение «ломает» сравнения, итоги и соединения. Всегда явно пишите ИНАЧЕ, даже если это пустая строка или ноль.
Вторая ошибка — несовместимость типов в ветках: например, ТОГДА "Нет данных" при ИНАЧЕ с числовым полем. Запрос либо не выполнится, либо тип колонки станет составным, что мешает сортировке и итогам. Приводите значения к одному типу.
Третья группа проблем — логика условий: диапазоны проверок должны идти от строгого к мягкому. Если поставить КОГДА Сумма > 10000 перед КОГДА Сумма > 100000, крупные суммы никогда не попадут во вторую ветку — сработает первая.
Проверка результата и ограничения
После добавления ВЫБОР проверьте отчёт на контрольном наборе данных: подберите документы, которые гарантированно попадают в каждую ветку условия, и убедитесь, что каждая ветка реально срабатывает. Ветка, не покрытая данными, часто скрывает опечатку в условии.
Отдельно проверьте граничные значения: суммы, равные порогу, пустые даты, NULL в полях. Помните, что любое сравнение с NULL даёт ложь — если поле может быть NULL, обработайте его через ЕСТЬ NULL или ЕСТЬNULL до основного условия.
Ограничения, о которых стоит помнить: в вычисляемых полях СКД нельзя обращаться к функциям встроенного языка напрямую (только через общие модули с особыми настройками), а в запросе нельзя использовать функции языка выражений компоновки. Глубоко вложенные ВЫБОР (более 4–5 уровней) ухудшают читаемость — их лучше заменить соединением с таблицей соответствий или вынести логику в код.
Как проверить результат
Каждая строка содержит одно из ожидаемых значений, пустых ячеек нет
Пустые ячейки или NULL — нет ветки ИНАЧЕ или не обработан NULL
Итог равен сумме детальных строк по условию
Итог пуст или расходится — проверьте «Рассчитывать по» и ИНАЧЕ 0
Отчёт формируется за приемлемое время
Резкое замедление — условие вынесено в вычисляемое поле вместо запроса
Частые вопросы
Можно ли использовать ВЫБОР в отборе СКД?
Напрямую в отборе написать ВЫБОР нельзя — отбор сравнивает поле со значением. Но можно создать в запросе поле с ВЫБОР и накладывать отбор уже на него. Либо используйте в отборе составные условия через группы «И»/«ИЛИ».
Чем ВЫБОР отличается от ЕСТЬNULL?
ЕСТЬNULL(Поле, Значение) — частный случай: заменяет NULL указанным значением. ВЫБОР универсальнее и проверяет любые условия, но для обработки NULL короче и читаемее именно ЕСТЬNULL.
Почему запрос с ВЫБОР выдаёт ошибку «Несовместимые типы»?
Ветки ТОГДА и ИНАЧЕ возвращают разные типы, например строку и число или ссылку и строку. Приведите ветки к одному типу: замените текстовую заглушку на значение нужного типа или используйте ВЫРАЗИТЬ.
Как написать ВЫБОР с условием по параметру отчёта?
В запросе параметр доступен через амперсанд: ВЫБОР КОГДА &Вариант = 1 ТОГДА Поле1 ИНАЧЕ Поле2 КОНЕЦ. Убедитесь, что параметр обязательно заполнен, иначе условие не сработает.
Можно ли вкладывать ВЫБОР внутрь ВЫБОР?
Да, вложенность не ограничена синтаксисом: ВЫБОР КОГДА … ТОГДА ВЫБОР КОГДА … КОНЕЦ ИНАЧЕ … КОНЕЦ. Но при глубине больше трёх уровней выражение трудно читать — лучше перейти на последовательные КОГДА или соединение с таблицей соответствий.
Работает ли ВЫБОР в наборе данных типа «Объект»?
Нет, оператор ВЫБОР доступен только в запросах. Для набора «Объект» условная логика реализуется в коде, формирующем таблицу, либо уже в вычисляемых полях СКД функцией Выбор().
Что важно запомнить
ВЫБОР КОГДА ТОГДА ИНАЧЕ КОНЕЦ пишется в запросе набора данных, Выбор(усл., зн1, зн2) — в вычисляемых полях, а условные итоги строятся как Сумма(Выбор(...)) в ресурсах. Всегда задавайте ИНАЧЕ, держите типы веток одинаковыми, проверяйте NULL и порядок условий, а тяжёлую логику оставляйте в запросе, а не в вычисляемых полях.