Почему не работает ЕСТЬNULL в СКД и как правильно вывести ноль вместо пустого поля

Программист 1С v8.3 (Управляемые формы) Управленческий учет Торговля и дистрибуция
← На главную

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

Анализируем причину проблемы: почему ЕСТЬNULL «молчит»

Разберем ситуацию, с которой столкнулся автор темы. В запросе используется виртуальная таблица Обороты регистра накопления. Когда мы пишем ЕСТЬNULL(ПродажиОбороты.СтоимостьОборот, 0), мы ожидаем, что если продаж не было, система вернет 0. Однако это работает только в том случае, если в выборке базы данных существует сама строка, но значение в конкретной колонке равно NULL.

В случае с виртуальными таблицами оборотов ситуация иная: если за выбранный период по конкретной номенклатуре или контрагенту движений не было, база данных вообще не возвращает строку для этой комбинации измерений. Функции ЕСТЬNULL просто не к чему примениться — строки нет. Когда СКД начинает объединять данные из разных наборов или периодов (например, через полное соединение), она сама «достраивает» отсутствующие строки, и именно в этих местах возникают «пустоты» (значения NULL), которые ваш исходный запрос обработать уже не мог.

Решение №1: Использование пакетного запроса с ОБЪЕДИНИТЬ ВСЕ

Наиболее надежным и производительным способом в 1С считается отказ от нескольких наборов данных в пользу одного пакетного запроса с использованием конструкции ОБЪЕДИНИТЬ ВСЕ. Это позволяет подготовить данные таким образом, чтобы в итоговой выборке всегда присутствовали числовые значения, даже если в одном из периодов оборотов не было.

Рассмотрим структуру такого запроса по шагам:

  1. Первая временная таблица (ВТ1): Выбираем данные за первый период (например, прошлый год).
  2. Вторая временная таблица (ВТ2): Выбираем данные за второй период (текущий год).
  3. Объединение данных: Собираем данные из обеих таблиц в одну общую таблицу, подставляя 0 в те колонки, данных для которых в текущем периоде нет.

Посмотрим на пример реализации такого подхода:


// Выбираем данные за прошлый период
ВЫБРАТЬ
    ПродажиОбороты.Номенклатура КАК Номенклатура,
    ПродажиОбороты.СтоимостьОборот КАК СтоимостьПрошлыйГод,
    0 КАК СтоимостьТекущийГод
ПОМЕСТИТЬ ВТ_Данные
ИЗ
    РегистрНакопления.Продажи.Обороты(&НачалоПрошлогоПериода, &КонецПрошлогоПериода, , ) КАК ПродажиОбороты

ОБЪЕДИНИТЬ ВСЕ

// Выбираем данные за текущий период
ВЫБРАТЬ
    ПродажиОбороты.Номенклатура,
    0,
    ПродажиОбороты.СтоимостьОборот
ИЗ
    РегистрНакопления.Продажи.Обороты(&НачалоПериода, &КонецПериода, , ) КАК ПродажиОбороты;

////////////////////////////////////////////////////////////////////////////////
// Группируем данные в итоговой выборке
ВЫБРАТЬ
    ВТ.Номенклатура КАК Номенклатура,
    СУММА(ВТ.СтоимостьПрошлыйГод) КАК СтоимостьПрошлыйГод,
    СУММА(ВТ.СтоимостьТекущийГод) КАК СтоимостьТекущийГод
ИЗ
    ВТ_Данные КАК ВТ
СГРУППИРОВАТЬ ПО
    ВТ.Номенклатура

При таком подходе СКД получит готовую таблицу, где вместо отсутствующих данных стоят реальные нули. Это гарантирует корректную работу математических операций в ресурсах.

Решение №2: Правильный расчет процентов в ресурсах СКД

Часто программисты допускают ошибку, пытаясь рассчитать процент роста или падения прямо в тексте запроса. Проанализируем, к чему это приводит: если в строках процент считается верно, то в Общих итогах СКД просто просуммирует эти проценты, выдав абсурдное число (например, 700% вместо реальных 15%).

Для корректного расчета итогов формулу нужно писать не в запросе, а на закладке «Ресурсы» схемы компоновки данных. Рассмотрим правильную формулу для поля РостПадениеПроцент:

Неправильно: Сумма(РостПадениеПроцент)

Правильно:


ВЫБОР 
    КОГДА СУММА(СтоимостьПрошлыйГод) = 0 ТОГДА 0 
    ИНАЧЕ (СУММА(СтоимостьТекущийГод) - СУММА(СтоимостьПрошлыйГод)) / СУММА(СтоимостьПрошлыйГод) * 100 
КОНЕЦ

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

Решение №3: Текст значения NULL (визуальное оформление)

Если ваша задача состоит исключительно в том, чтобы «красиво» показать ноль пользователю, а математические расчеты при этом уже работают корректно, можно воспользоваться встроенными средствами оформления СКД, не переписывая запрос.

Разберем этот метод по шагам:

  1. Перейдем на закладку «Наборы данных».
  2. Найдем нужное числовое поле.
  3. В колонке «Оформление» нажмем на кнопку выбора.
  4. В появившемся окне найдем параметр «Текст значения NULL».
  5. Впишем в это поле значение 0.

Важный момент: это изменение носит чисто визуальный характер. Если вы попытаетесь использовать это поле в вычисляемых полях или ресурсах без функции ЕСТЬNULL, система все равно будет видеть там пустоту, что может привести к ошибкам в расчетах.

Решение №4: Вычисляемые поля как альтернатива

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

ЕСТЬNULL(СтоимостьОборот, 0) - ЕСТЬNULL(СтоимостьОборотПрошлыйПериод, 0)

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

Подведем итоги

Мы выяснили, что причина «неработающего» ЕСТЬNULL кроется в отсутствии самих строк в результатах виртуальных таблиц. Для создания качественного и отказоустойчивого отчета мы рекомендуем:

Следуя этим правилам, вы сможете избежать типичных ошибок при работе с СКД и обеспечить высокую точность аналитических данных в ваших отчетах.

← На главную