|
Помогите составить рекурсивную функцию | ☑ | ||
---|---|---|---|---|
0
hatsher
09.08.12
✎
14:11
|
документ может вводиться на основании самого себя(такого же объекта МД).
Требуется по документу найти все документы, введенные на его основании + все документы, введенные на основании этих+ и тд |
|||
1
izekia
09.08.12
✎
14:12
|
зачем рекурсию?
|
|||
2
hatsher
09.08.12
✎
14:13
|
а как по-другому? я не могу в запросе соединять бесконечное число таблиц..
|
|||
3
izekia
09.08.12
✎
14:13
|
а рекурсию ты в запросе можешь?
|
|||
4
Wobland
09.08.12
✎
14:14
|
этот глист страдал глистами, что мучались глистами сами
|
|||
5
hatsher
09.08.12
✎
14:14
|
(3) я могу составить рекурсивную функцию, которая будет использовать запрос.. но может можно как-то проще
|
|||
6
Маратыч
09.08.12
✎
14:15
|
(5) А как еще проще? Все верно, функция с запросом.
|
|||
7
izekia
09.08.12
✎
14:15
|
(5) запрос в рекурсии - это еще тот быдлокод
|
|||
8
izekia
09.08.12
✎
14:16
|
хотя здесь без разницы, но рекурсия точно не нужна
|
|||
9
Alex S D
09.08.12
✎
14:17
|
а типовой отчет по структуре подчиненности не прет?
|
|||
10
Маратыч
09.08.12
✎
14:17
|
(7) Ну через Док.ДокОснование без запроса. Какая разница? Быдлокод - это запрос в цикле, когда без цикла можно обойтись. А в рекурсии вполне уместно.
|
|||
11
hatsher
09.08.12
✎
14:17
|
(8) какой алгоритм примерно?
|
|||
12
Маратыч
09.08.12
✎
14:17
|
(8) Дык если длина цепочки неизвестна, без рекурсии как?
|
|||
13
Mort
09.08.12
✎
14:21
|
У хрусталевой есть пример построения в СКД своей иерархии. Не гарантирую что взлетит, не приходилось на практике как-то...
|
|||
14
izekia
09.08.12
✎
14:23
|
тест запроса упростил:
запрос = Новый Запрос("ВЫБРАТЬ Ссылка ИЗ Документ.МойДокумент ГДЕ Основание = &Основание"); результат = Новый Массив; результат.Добавить(ИсходныйДокумент); счетчик = 0; Пока результат.Количество() > счетчик Цикл запрос.УстановитьПараметр("Основание", результат[счетчик]); выборка = запрос.Выполнить().Выбрать(); Пока выборка.Следующий() Цикл результат.Добавить(выборка.Ссылка); КонецЦикла; счетчик = счетчик + 1; КонецЦикла; |
|||
15
izekia
09.08.12
✎
14:24
|
сорри за (7) в данном случае в рекурсии запрос - это не быдлокод, просто изначально неправильно представил себе структуру
|
|||
16
hatsher
09.08.12
✎
14:26
|
спасибо
|
|||
17
izekia
09.08.12
✎
14:26
|
в данном случае рекурсия - это зло, здесь мы добавляем всего одну переменную и сразу же создаем необходимый список документов и его же и обходим
|
|||
18
Mort
09.08.12
✎
14:26
|
+(13) Собсна не вижу причин, чтобы не взлетело.
|
|||
19
hatsher
09.08.12
✎
14:26
|
+ а можно усложнить задачу:)
|
|||
20
Ненавижу 1С
гуру
09.08.12
✎
14:26
|
(13) что вы возитесь со своей СКД как панацеей
СКД выполняется не в СУБД, а на сервере приложений, также может и обычный код, только СКД неуправляем внутри себя, ты просто что-то получаешь, но не знаешь как оно получено, оптимальностью управлять нельзя |
|||
21
izekia
09.08.12
✎
14:27
|
(18) зачем усложнять?
|
|||
22
izekia
09.08.12
✎
14:27
|
(19) давай
|
|||
23
hatsher
09.08.12
✎
14:29
|
(21) исходная задача прост немного сложнее:
докМД1 вводится только на основании себя. ДокМД2 вводится только на основании ДокаМД1 требуется найти найти все ДокМД2, у которых в основании по иерархии имеется ИсходныйДокумент |
|||
24
Mort
09.08.12
✎
14:29
|
(20) Гм. На СКД это делается быстро. Только звучит страшно. Конечно можно и кодом, но это точно не будет запрос в цикле :)
|
|||
25
Mort
09.08.12
✎
14:29
|
+(24) быстро в смысле не оптимально, а время потраченное на разработку.
|
|||
26
Mort
09.08.12
✎
14:31
|
+ И не думаю что одинэсный транслятор в силах обогнать платформенные функции СКД.
|
|||
27
hatsher
09.08.12
✎
14:31
|
+ впронципе можно получить массив по 14 и найти все докМД2 по нахождению докОснование в этом массиве..
|
|||
28
izekia
09.08.12
✎
14:34
|
запрос = Новый Запрос("ВЫБРАТЬ Ссылка ИЗ Документ.МойДокумент ГДЕ Основание = &Основание");
основания = Новый СписокЗначений; основания.Добавить(ИсходныйДокумент); счетчик = 0; Пока основания.Количество() > счетчик Цикл запрос.УстановитьПараметр("Основание", основания[счетчик].Значение); выборка = запрос.Выполнить().Выбрать(); Пока выборка.Следующий() Цикл основания.Добавить(выборка.Ссылка); КонецЦикла; счетчик = счетчик + 1; КонецЦикла; запрос = Новый Запрос("ВЫБРАТЬ Ссылка ИЗ Документ.МойДокумент2 ГДЕ Основание В &Основания" запрос.УстановитьПараметр("Основания", основания); |
|||
29
izekia
09.08.12
✎
14:35
|
(26) хочешь потестить?)
|
|||
30
izekia
09.08.12
✎
14:35
|
(24) пример дай? я просто этот код написал не открывая 1С, это про скорость разработки
|
|||
31
hatsher
09.08.12
✎
14:36
|
(28) Спасибо!
|
|||
32
Classic
09.08.12
✎
14:36
|
(28)
Не отработан вариант при котором два документа - основания друг-друга |
|||
33
hatsher
09.08.12
✎
14:37
|
(32) это врядли:) пользователю недоступно менять основание документа
|
|||
34
Mort
09.08.12
✎
14:37
|
(29) Как нибудь попробую.
(28) Этот код можно значительно оптимизировать, посылая запрос не на каждый документ, а на полученный ряд доков по основанию. Таким образом количество запросов будет равно количеству вложений, что не так уж много. |
|||
35
Classic
09.08.12
✎
14:37
|
(33)
Все равно не аккуратненько :) Хотя хороший пример как обойтись без рекурсии |
|||
36
izekia
09.08.12
✎
14:38
|
(34) да, согласен
|
|||
37
izekia
09.08.12
✎
14:39
|
(35) циклические ссылки вряд ли допустимы чисто логически, можно проверять на вхождение
|
|||
38
izekia
09.08.12
✎
14:39
|
сейчас добавлю (32) и (34)
|
|||
39
Ненавижу 1С
гуру
09.08.12
✎
14:45
|
(24) то есть ты утверждаешь, что СКД построит эту иерархию без запроса в цикле?
|
|||
40
izekia
09.08.12
✎
14:50
|
запрос = Новый Запрос("ВЫБРАТЬ МД.Ссылка ИЗ Документ.МойДокумент КАК МД ГДЕ МД.Основание В &Основания");
основания = Новый Массив; основания.Добавить(ИсходныйДокумент); основанияДляЗапроса = Новый СписокЗначений; основанияДляЗапроса.Добавить(ИсходныйДокумент); Пока Истина Цикл запрос.УстановитьПараметр("Основание", основанияДляЗапроса); выборка = запрос.Выполнить().Выбрать(); основанияДляЗапроса.Очистить(); Пока выборка.Следующий() Цикл Если основания.Найти(выборка.Ссылка) = Неопределено Тогда основания.Добавить(выборка.Ссылка); основанияДляЗапроса.Добавить(выборка.Ссылка); КонецЕсли; КонецЦикла; Если основанияДляЗапроса.Количество() = 0 Тогда Прервать; КонецЕсли; КонецЦикла; запрос = Новый Запрос("ВЫБРАТЬ МД2.Ссылка ИЗ Документ.МойДокумент2 КАК МД2 ГДЕ МД2.Основание В &Основания" основанияДляЗапроса.Загрузить(основания); запрос.УстановитьПараметр("Основания", основания); |
|||
41
Mort
09.08.12
✎
14:51
|
(39) Ну зуб бы не поставил (уже мало осталось) но по описанию сего чуда в хрусталевой, СКД строит подобную иерархию также как и для простых иерархических справочников. Отсюда предположение.
|
|||
42
Mort
09.08.12
✎
14:51
|
*так же
|
|||
43
hatsher
09.08.12
✎
14:53
|
надо бы добавить к БЗ
|
|||
44
izekia
09.08.12
✎
14:54
|
кстати, более забавная идея появилась)
сейчас попробую написать |
|||
45
Ненавижу 1С
гуру
09.08.12
✎
15:00
|
(41) открою секрет, простую иерархию она тоже строит в цикле
|
|||
46
izekia
09.08.12
✎
15:04
|
+ (44) не, нет возможности дополнять временные таблицы, а так бы можно было красиво сделать
|
Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |