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