Способы обхода результата запроса
Первый, и самый простой способ обхода - линейный. При линейном обходе выборка будет выдавать записи в той последовательности, в которой они располагаются в результате запроса. В нашем примере это будут записи с номерами 1, 2, 3, 4, 5 и так далее до записи с номером 20.
Для получения линейной выборки из результата необходимо вызвать метод Выбрать объекта РезультатЗапроса без параметров, либо с параметром ОбходРезультатаЗапроса.Прямой.
Пример:
СпособВыборки = ОбходРезультатаЗапроса.Прямой;
Выборка1 = РезультатЗапроса.Выбрать(СпособВыборки);
// что равнозначно записи
Выборка1 = РезультатЗапроса.Выбрать();
Иерархический обход результата
Следующий способ обхода результата - иерархический. При данном обходе обходятся только записи, находящиеся на одном уровне. Для получения иерархической выборки из результата необходимо вызвать метод Выбрать объекта РезультатЗапроса с параметром ОбходРезультатаЗапроса.ПоГруппировкамСИерархией.
СпособВьборки = ОбходРезультатаЗапроса.ПоГруппировкамСИерархией;
Выборка2 = РезультатЗапроса.Выбрать(СпособВыборки);
Выборка из результата с иерархическим обходом в нашем примере обойдет только записи с номерами 1 и 11, так как только эти две записи находятся на самом верхнем уровне. Проиллюстрируем это, представив наш результат в виде дерева, где узлами будут итоговые записи, а листьями дерева будут детальные записи. Вот что у нас получится:
1 | Сантехника | 104 | ||
2 | Кран | 84 | ||
3 | Кран | 10 | ||
4 | Кран | 8 | ||
5 | Кран | 44 | ||
6 | Кран | 22 | ||
7 | Смеситель | 20 | ||
8 | Смеситель | 5 | ||
9 | Смеситель | 1 | ||
10 | Смеситель | 14 | ||
11 | Мебель | 134 | ||
12 | Стол | 26 | ||
13 | Стол | 1 | ||
14 | Стол | 15 | ||
15 | Стол | 10 | ||
16 | Стул | 108 | ||
17 | Стул | 55 | ||
18 | Стул | 5 | ||
19 | Стул | 32 | ||
20 | Стул | 16 |
Из этого рисунка видно, что именно записи с номерами 1 и 11, и только они находятся на первом уровне дерева, в результате чего только они и попадают в первый проход иерархической выборки.
Возникает вопрос, как получать остальные записи результата запроса. Для этого у объекта ВыборкаИзРезультатаЗапроса можно получить еще одну выборку, которая будет обходить подчиненные записи текущей записи выборки. В нашем примере в момент, когда объект Выборка2 будет позиционирован на запись с номером 1, мы запросим у него иерархическую выборку. Таким образом, мы получим выборку, которая нам вернет записи с номерами 2, 7. А когда Выборка2 будет спозиционирована на записи с номером 11, то полученная у нее иерархическая выборка вернет записи с номерами 12, 16. Так реализуется иерархический обход результатов запроса Заметим, что у выборки можно получать вложенные выборки любого типа. Так, если бы мы запросили у Выборки2, спозиционированной на записи 1, линейную выборку, то с ее помощью мы бы получили записи с номерами записей со 2-го по 10-й. Проиллюстрируем описанную методику на примере.
Пример:
Процедура ВыдатьРекурсивно(Выборка) Далее;
Процедура ВыполнитьЗапрос()
Запрос = Новый Запрос;
Текст = "Выбрать Товар, Количество
| Из Документ.РасхНакя.Состав
| Упорядочить по Товар
| Итоги Сумма(Количество) По Товар, Товар Иерархия";
РезультатЗапроса = Запрос.Выполнить();
// Получим выборку из результата запроса.
СпособВыборки = ОбходРезультатаЗапроса.ПоГруппировкамСИерархией;
Выборка = РезультатЗапроса.Выбрать(СпособВыборки);
ВыдатьРекурсивно(Выборка);
КонецПроцедуры
Процедура ВыдатьРекурсивно(Выборка)
// Пока в выборке есть записи ...
Пока Выборка. Следующий () Цикл
// ... выведем в окно сообщений поля из результата
Товар = Выборка.Наименование;
Количество = Выборка.Количество;
Сообщить("Товар: " + Товар + " Количество: " + Количество);
// продолжим выборку подчиненных записей
СпособВыборки = ОбходРезультатаЗапроса.ПоГруппировкамСИерархией;
Выдать Рекурсивно(Выборка.Выбрать(СпособВыборки));
КонецЦикла;
КонецПроцедуры
Обход результата по группам
Третий, и последний способ обхода результата - по группам. Он сходен с иерархическим обходом, но с одним различием: записи с иерархическими итогами при обходе в нем рассматриваются как детальные записи, а не как узловые. Для получения выборки по группам из результата запроса необходимо вызвать метод Выбрать
объекта РезультатЗапроса с
параметром ОбходРезультатаЗапроса.ПоГруппировкам.
Пример:
СпособВыборки = ОбходРезультатаЗапроса.ПоГруппировкам;
Вы6орка2 = РезультатЗапроса.Выбрать(СпособВыборки);
Перебрав в ней всё, мы получим записи с номерами 1, 2, 7, 11, 12, 16.
Пример:
Процедура ВыдатьДочерниеЗаписи(Выборка) Далее;
Процедура ВыполнитьЗапрос()
Запрос = Новый Запрос;
Текст = "Выбрать Товар, Количество
| Из Документ.РасхНакя.Состав
| Упорядочить по Товар
| Итоги Сумма(Количество) По Товар, Товар Иерархия";
РезультатЗапроса = Запрос.Выполнить();
// Получим выборку из результата запроса.
СпособВыборки = ОбходРезультатаЗапроса.ПоГруппировкам;
Выборка = РезультатЗапроса.Выбрать(СпособВыборки);
// Пока в выборке есть записи ...
Пока Выборка.Следующий() Цикл
// ... выведем в окно сообщений доля из результата
Товар = Выборка.Наименование;
Количество = Выборка.Количество;
Сообщить("Товар: " + Товар + " Итого по товару: " + Количество) ;
ВыдатьДочерниеЗаписи(Выборка.Выбрать()) ;
КонецЦикла;
КонецПроцедуры
Процедура ВыдатьДочерниеЗапися (Выборка)
// Пока в выборке есть записи . . .
Пока Выборка.Следующий() Цикл
// ... выведем в окно сообщений поля из результата
Товар = Выборка.Наименование;
Количество = Выборка.Количество;
Сообщить("Товар: " + Товар + " Количество: " + Количество);
КонецЦикла;
КонецПроцедуры