При разработке отчетов на базе Системы компоновки данных (СКД) разработчики часто сталкиваются с ситуацией, когда в отчете типа «Кросс-таблица» строки по измерениям не объединяются (не «сворачиваются»), а выводятся отдельными строками для каждой колонки по диагонали или лесенкой. Разберем по шагам, почему возникает такое поведение при использовании набора данных типа Объект (таблица значений) и как правильно настроить структуру отчета.
Рассмотрим типичную ситуацию: в отчет передается готовая таблица значений, содержащая поля Номенклатура, Склад и Количество. Задача — получить классическую кросс-таблицу, где в строках выводятся товары, в колонках — склады, а на пересечении — остаток или оборот.
При неверной настройке структуры отчета формируется результат следующего вида:
Товар 1 | 5 | 0 | 0
Товар 2 | 2 | 0 | 0
Товар 1 | 0 | 2 | 0
Товар 2 | 0 | 4 | 0
Товар 1 | 0 | 0 | 3
Вместо ожидаемого свернутого представления:
Товар 1 | 5 | 2 | 3
Товар 2 | 2 | 4 | 0
Выясним причину такого поведения. В СКД тип набора данных (будь то Запрос или Объект) не влияет на правила агрегации и вывода строк в отчете. За объединение строк отвечает исключительно структура настроек отчета. Если в строках таблицы добавить элемент «Детальные записи» (пустая группировка), компоновщик данных добросовестно выведет каждую запись исходного набора данных отдельной строкой. Так как одна и та же номенклатура встречается в источнике данных на разных складах в разных строках, для каждой строчки таблицы значений будет сформирована своя строка в отчете.
Разберем последовательность действий для корректной настройки отчета:
В схеме компоновки данных перейдем на вкладку «Настройки». В корне структуры добавим элемент «Таблица». В ветку «Строки» необходимо добавить группировку с указанием поля Номенклатура (вместо элемента «Детальные записи»). В ветку «Колонки» добавляем группировку с указанием поля Склад.
Перейдем на вкладку «Ресурсы» схемы компоновки данных. Добавим поле Количество и укажем для него агрегатную функцию в выражении:
Сумма(Количество)
Без добавления поля на вкладку «Ресурсы» СКД воспринимает числовое поле как обычный реквизит и не может выполнить его агрегацию на пересечении строк и колонок.
На уровне группировки строк (Номенклатура) в выбранные поля достаточно добавить поле Количество (или оставить системное Автополе, если Количество выбрано в общих выбранных полях отчета). Поле ресурса не должно быть добавлено в поля группировки — только в выбранные поля.
Проанализируем важные нюансы, которые необходимо учитывать при передаче ТаблицыЗначений в СКД:
В отличие от набора данных Запрос, где операцию агрегации можно переложить на СУБД с помощью инструкции СГРУППИРОВАТЬ ПО, при использовании набора данных Объект вся группировка и расчет ресурсов выполняются процессором компоновки в оперативной памяти. Для ускорения компоновки и экономии памяти исходную таблицу перед передачей в отчет рекомендуется предварительно свернуть:
// Предварительная подготовка данных перед передачей в СКД
ТаблицаТоваров.Свернуть("Номенклатура, Склад", "Количество");
ВнешниеНаборыДанных = Новый Структура;
ВнешниеНаборыДанных.Вставить("ТаблицаТоваров", ТаблицаТоваров);
ПроцессорКомпоновки = Новый ПроцессорКомпоновкиДанных;
ПроцессорКомпоновки.Инициализировать(МакетКомпоновки, ВнешниеНаборыДанных);
СКД крайне чувствительна к типам данных в переданной таблице. Если колонка не типизирована или содержит значения разных типов (например, ссылку и Неопределено или строку), компоновщик разделит их на разные строки группировки.
Значения Null, Неопределено и пустая ссылка типа СправочникСсылка.Номенклатура воспринимаются СКД как три разных значения и образуют три независимые строки отчета. Всегда следите за чистотой данных в исходной таблице.
Таким образом, для получения свернутой кросс-таблицы в СКД всегда используйте явные группировки по измерениям в строках и колонках таблицы и объявляйте числовые показатели на вкладке «Ресурсы» схемы компоновки данных.