powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Программирование [игнор отключен] [закрыт для гостей] / Как эффективно искать пути в N-арном дереве?
7 сообщений из 7, страница 1 из 1
Как эффективно искать пути в N-арном дереве?
    #35006033
Divog
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Есть задача хранить дерево размножения животных. Т.е. две вершины (отэць, мат) у них куча детей. Получается, что у каждой вершины 0-2 предка и 0-N потомков.
В принципе хранить все это легко получается, просто указывая для каждой вершины ее двух предков, если бы не одно но.
Так-же, помимо хранения необходимо уметь находить пути (или хотя бы один кратчайший путь) между двумя вершинами. Другими словами проверять родство двух животных. Вроде в каком колене у них там где общий предок или потомок одного где-то родственник предка другого и т.п.
Делать это с помощью рекурсивного просмотра всех возможных путей, очень накладно.

В связи с чем прошу пнуть в верном направлении, про какие деревья, их представления да алгоритмы почитать, чтобы понять, как пооптимальнее решить эта задачу.
Или здесь кроме рекурсии никак?
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35006136
teras
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Divog wrote:
> родство двух животных. Вроде в каком колене у них там где общий предок
> или потомок одного где-то родственник предка другого и т.п.
> Делать это с помощью рекурсивного просмотра всех возможных путей, очень
> накладно.

Интересует проверить родство (найти общего предка) или узнать точный
путь? Это разные задачи.

Если родство - можно гнать волну вверх по дереву. Точнее две волны, по
одной из каждого узла. Для этого узлы, составляющие фронт волны
объединяется в список. Кроме того, к каждому узлу добавляется цвет
(белый=не видели, красный=видели из узла a, синий=видели из узла b). На
каждом шаге фронт волны распространяется вверх к предкам. Для этого
проверяется цвет вершины предка - белая попадает в новый фронт и
перекрашивается, вершина соответствующая своему цвету - игнорируется,
вершина чужого цвета - ближайший общий предок.

Если нужно точно найти пути, то задача несколько усложняется. Придется
еще хранить ссылку на узел при переходе из которого вершина была
перекрашена.

>
> В связи с чем прошу пнуть в верном направлении, про какие деревья, их
> представления да алгоритмы почитать, чтобы понять, как пооптимальнее
> решить эта задачу.

Оптимальность зависит от условий. Как вариант - найти транзитивное
замыкание отношения предок для каждого из узлов и взять их пересечение.
Posted via ActualForum NNTP Server 1.4
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35011923
Divog
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
авторИнтересует проверить родство (найти общего предка) или узнать точный
путь? Это разные задачи.
Надо найти именно путь.

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

авторОптимальность зависит от условий. Как вариант - найти транзитивное
замыкание отношения предок для каждого из узлов и взять их пересечение.

Сейчас так и делаю, однако построение оного, при моей схеме хранения данных оч. накладно, да и великоватое оно получается, если там предков 20 колен. 2*2^20 пар id-шников.

Думал, может что пооптимальнее есть. Вы мне дайте ключевых слов, я в инете найду доки, почитаю :)
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35012343
teras
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Divog wrote:

>> Оптимальность зависит от условий. Как вариант - найти транзитивное
>> замыкание отношения предок для каждого из узлов и взять их пересечение.
>
> Сейчас так и делаю, однако построение оного, при моей схеме хранения
> данных оч. накладно, да и великоватое оно получается, если там предков
> 20 колен. 2*2^20 пар id-шников.

А как находите путь? Замыкания ведь недостаточно. Просто поиск по
отношению прямой предок до заданного предка?

Пофантазирую еще. Может скрестить транзитивное замыкание отношения
прямой предок и волновой поиск? Отношение предок позволяет относительно
быстро проверить существование общего предка для двух особей, но не
показывает пути. И в вашей задаче это отношение можно строить по мере
роста. Скрещивание будет заключаться в том, что на каждой итерации волна
распространяется только на те узлы, у которых есть общий предок со
второй особью. Таким образом все сторонние ветви отмирают сразу.

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

>
> Думал, может что пооптимальнее есть. Вы мне дайте ключевых слов, я в
> инете найду доки, почитаю :)

Не, с ключевыми словами - сложно. Очевидно, что задача из области
дискретной математики и теория графов, но это слишком общо. Приведенный
волновой алгоритм применяется в области трассировки печатных плат.
Можно, конечно еще покопаться в ней, возможно что-нибудь найдете:
<http://algolist.manual.ru/maths/graphs/shortpath/smartmove.php>

Опять-же, если бы у вас и в самом деле было дерево, а не ациклический
орграф, можно было бы подумать о множественной модели представления
дерева <http://www.sedinko.ru/algo/doc1.php>. Вот пожалуй и все, что
приходит в голову.
Posted via ActualForum NNTP Server 1.4
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35012378
apapacy
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Почему ацикличный?
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35012405
teras
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
apapacy wrote:
> Почему ацикличный?

А как вы себе представляете цикл в данном случае? Как можно быть прямым
или косвенным предком самого себя?
Posted via ActualForum NNTP Server 1.4
...
Рейтинг: 0 / 0
Как эффективно искать пути в N-арном дереве?
    #35021889
Divog
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Прошу прощения, чуток пропал :)

В общем прикинул я, для реальных данных (ожидаемых) волнового поиска, описанного Вами выше, будет достаточно. И по памяти хорошо и по скорости нормально, учитывая, что в большинстве случаев уже где-то на 5-10-м колене будет результат. И для худших случаев где 20-ые колена, сносно будет работать.
А если что, то отношение прореженное можно будет прикрутить без больших переделок.

Спасибо за помощь и за ссылки. Почитаю на досуге :)
...
Рейтинг: 0 / 0
7 сообщений из 7, страница 1 из 1
Форумы / Программирование [игнор отключен] [закрыт для гостей] / Как эффективно искать пути в N-арном дереве?
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]