Получить иерархию подразделений в запросе
Добрый день господа.
Необходимо получить таблицу в которой каждому подразделению (элементу справочника с иерархией элементов) будут сопоставлены все подразделения входящие в него на любом уровне вложенности. То-есть вся иерархия подразделений.
Например есть иерархия:
Подр1
+-Подр2
| +-Подр3
| | +-Подр4
Получим :
Подр1 Подр2
Подр1 Подр3
Подр1 Подр4
Подр2 Подр3
Подр2 Подр4
Подр3 Подр4
....................................
Можно такое сделать в одном запросе?
Необходимо получить таблицу в которой каждому подразделению (элементу справочника с иерархией элементов) будут сопоставлены все подразделения входящие в него на любом уровне вложенности. То-есть вся иерархия подразделений.
Например есть иерархия:
Подр1
+-Подр2
| +-Подр3
| | +-Подр4
Получим :
Подр1 Подр2
Подр1 Подр3
Подр1 Подр4
Подр2 Подр3
Подр2 Подр4
Подр3 Подр4
....................................
Можно такое сделать в одном запросе?
По теме из базы знаний
Ответы
Подписаться на ответы
Инфостарт бот
Сортировка:
Древо развёрнутое
Свернуть все
Сделайте подзапрос подразделений с пустым Родителем, и ещё один подзапрос с подразделениями у которых Родитель заполнен. А потом соедините левым соединением две полученных таблицы с условием Таблица2.Подразделение В ИЕРАРХИИ(Таблица1.Подразделение).
(11) Да Вы правы, универсального запроса не сделать, по крайней мере у меня не получилось.
(1) Извините что ввел в заблуждение.
Однако, получилось сделать запрос с фиксированным количеством вложенных группировок:
Правда на уровне SQL наверное там страшный код будет...
(1) Извините что ввел в заблуждение.
Однако, получилось сделать запрос с фиксированным количеством вложенных группировок:
ВЫБРАТЬ
Элементы.Родитель КАК Родитель,
Элементы.Подгруппа КАК Подгруппа
ИЗ
(ВЫБРАТЬ
Родители.Ссылка КАК Родитель,
Подчиненные.Подгруппа КАК Подгруппа,
Подчиненные.Родитель КАК РодительПодгруппы
ИЗ
Справочник.Подразделение КАК Родители
ЛЕВОЕ СОЕДИНЕНИЕ (ВЫБРАТЬ
Подразделение.Ссылка КАК Подгруппа,
Подразделение.Родитель КАК Родитель
ИЗ
Справочник.Подразделение КАК Подразделение
ГДЕ
Подразделение.Родитель <> ЗНАЧЕНИЕ(Справочник.Подразделение.ПустаяСсылка)
И Подразделение.ПометкаУдаления = ЛОЖЬ) КАК Подчиненные
ПО (Подчиненные.Родитель В ИЕРАРХИИ
(ВЫБРАТЬ
Подгруппы.Родитель
ИЗ
Справочник.Подразделение КАК Подгруппы
ГДЕ
Подгруппы.Родитель <> ЗНАЧЕНИЕ(Справочник.Подразделение.ПустаяСсылка)
И Подгруппы.ПометкаУдаления = ЛОЖЬ))
ГДЕ
Родители.Родитель = ЗНАЧЕНИЕ(Справочник.Подразделение.ПустаяСсылка)
И Родители.ПометкаУдаления = ЛОЖЬ) КАК Элементы
ГДЕ
(Элементы.РодительПодгруппы В (Элементы.Родитель)
ИЛИ Элементы.РодительПодгруппы.Родитель В (Элементы.Родитель)
ИЛИ Элементы.РодительПодгруппы.Родитель.Родитель В (Элементы.Родитель)
ИЛИ Элементы.РодительПодгруппы.Родитель.Родитель.Родитель В (Элементы.Родитель)
ИЛИ Элементы.РодительПодгруппы.Родитель.Родитель.Родитель.Родитель В (Элементы.Родитель))
УПОРЯДОЧИТЬ ПО
Родитель,
Подгруппа
АВТОУПОРЯДОЧИВАНИЕ
ПоказатьПравда на уровне SQL наверное там страшный код будет...
Предлагаю изящное решение с применением рекурсии
Объявляем СписокОтделений как Список Значений.
Перед каждым обращением к процедуре очищаем его.
Допустим, необходимо выбрать все отделения входящие в данное подразделение на всю глубину иерархии.
&НаСервере
Объявляем СписокОтделений как Список Значений.
Перед каждым обращением к процедуре очищаем его.
Допустим, необходимо выбрать все отделения входящие в данное подразделение на всю глубину иерархии.
&НаСервере
Процедура ВыборОтделенийВИерархии(Подразделение)
СписокОтделений.Добавить( Подразделение ); // Выводим сразу в Список Значений
Запрос = Новый Запрос;
Текст =
"ВЫБРАТЬ РАЗЛИЧНЫЕ
| Отделения.Ссылка КАК Ссылка
| ИЗ
| Справочник.СтруктураПредприятия КАК Отделения
| ГДЕ
| Отделения.Родитель = &Подразделение // Выбираем подразделения у которых исходное является родителем
|";
Запрос.УстановитьПараметр("Подразделение", Подразделение);
Запрос.Текст = Текст;
РезультатЗапроса = Запрос.Выполнить().Выбрать();
Если РезультатЗапроса.Количество() > 0 Тогда
Пока РезультатЗапроса.Следующий() Цикл
ВыборОтделенийВИерархии(РезультатЗапроса.Ссылка); // В каждом из подчиненных подразделений в свою очередь ищем вложенных
КонецЦикла;
КонецЕсли;
КонецПроцедуры
Показать
(18)
Отлично, спасибо!
Процедура ВыборОтделенийВИерархии(Подразделение)
СписокОтделений.Добавить( Подразделение ); // Выводим сразу в Список Значений
Запрос = Новый Запрос;
Текст =
"ВЫБРАТЬ РАЗЛИЧНЫЕ
| Отделения.Ссылка КАК Ссылка
| ИЗ
| Справочник.СтруктураПредприятия КАК Отделения
| ГДЕ
| Отделения.Родитель = &Подразделение // Выбираем подразделения у которых исходное является родителем
|";
Запрос.УстановитьПараметр("Подразделение", Подразделение);
Запрос.Текст = Текст;
РезультатЗапроса = Запрос.Выполнить().Выбрать();
Если РезультатЗапроса.Количество() > 0 Тогда
Пока РезультатЗапроса.Следующий() Цикл
ВыборОтделенийВИерархии(РезультатЗапроса.Ссылка); // В каждом из подчиненных подразделений в свою очередь ищем вложенных
КонецЦикла;
КонецЕсли;
КонецПроцедуры
ПоказатьСписокОтделений.Добавить( Подразделение ); // Выводим сразу в Список Значений
Запрос = Новый Запрос;
Текст =
"ВЫБРАТЬ РАЗЛИЧНЫЕ
| Отделения.Ссылка КАК Ссылка
| ИЗ
| Справочник.СтруктураПредприятия КАК Отделения
| ГДЕ
| Отделения.Родитель = &Подразделение // Выбираем подразделения у которых исходное является родителем
|";
Запрос.УстановитьПараметр("Подразделение", Подразделение);
Запрос.Текст = Текст;
РезультатЗапроса = Запрос.Выполнить().Выбрать();
Если РезультатЗапроса.Количество() > 0 Тогда
Пока РезультатЗапроса.Следующий() Цикл
ВыборОтделенийВИерархии(РезультатЗапроса.Ссылка); // В каждом из подчиненных подразделений в свою очередь ищем вложенных
КонецЦикла;
КонецЕсли;
КонецПроцедуры
Отлично, спасибо!
Для получения уведомлений об ответах подключите телеграм бот:
Инфостарт бот