|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
Реализация дерева поиска список сыновей25.02.2019, 09:48. Показов 13377. Ответов 25
Метки нет (Все метки)
Добрый день.
Нужно создать 2-а дерева поиска и хранить их "списком сыновей". В нужно вставить в А используя обратных обход. И вывести результат - А выводить прямым обходом, а В симметричным. Требуется реализовать начальное формирование деревьев А и В, путем добавления некоторой последовательности значений (узлов) в пустое дерево. После чего требуется реализовать заданную операцию над деревьями без использования каких-либо вспомогательных структур (списков, массивов и т.п.), работая только с узлами деревьев А и В. (Не знаю как можно отказаться от списков, если в них храниться структура дерева). Что такое "список сыновей" я представляю, все как описано на 2-ой миниатюре, но как это реализовать на С++?
1
|
|
| 25.02.2019, 09:48 | |
|
Ответы с готовыми решениями:
25
Реализация бинарного дерева поиска Реализация бинарного дерева поиска |
|
Комп_Оратор)
|
|
| 25.02.2019, 11:15 | |
|
Bonttpol, мне известны 2 и 3-деревья поиска. Потому как произвольные n-деревья могут иметь правила а могут быть произвольными. В вашем случае я вижу 3-дерево. Это, если реализовано как 2-дерево с возможностью равенства, должно обходиться рекурсивно, но с проходом центральной ветки до упора. То есть, даже в ноде список не нужен, - достаточно хранить.
Node * left, * central, * right;.То есть если меньше-> влево, если больше ->вправо и если равно -> по центру и до конца (тут от порождающего узла и до конца развилок уже быть не может). То есть выходы из рекурсии отличаются на один дополнительный случай. Но если, количество детей произвольно (таки да список), то с трудом представляю себе как это может быть деревом поиска. Bonttpol, вообще, если вам задают 3-деревья, то респект. Вы должны ориентироваться в 2-деревьях с балансировкой (как AVL BST так и красно-чёрное) лучше многих, кто уже и подзабыл как там и что.
0
|
|
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 25.02.2019, 11:41 [ТС] | |
|
Вторая картинка - это просто визуализированный пример того как я понимаю реализацию дерева поиска "списком сыновей". Я даже не уверена верный ли он.
Я не знаю как мне заполнить структуру произвольного дерева и хранить его подобным списком на C++?
0
|
|
|
Комп_Оратор)
|
||
| 25.02.2019, 12:36 | ||
|
Добавлено через 45 минут Bonttpol, перечитав условие, я могу предположить, что речь идёт об 2-BST. Под хранением, - возможно, имеется ввиду сохранение данных в файл. Требуется создать 2 экземпляра в которых использовать разные методы обхода (итерации) для операций добавления и вывода в поток (в т.ч. и в файловый). Если мои предположения верны, то задание запутывающе сформулировано. Последовательность хранения в файле названа списком, в то время как дополнительные списочные структуры (как и любые иные временные накопители) в памяти запрещены. Вы молчите и я пытаюсь догадаться, постарайтесь ответить. Тут главное вам понять задачу.
1
|
||
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 25.02.2019, 12:41 [ТС] | |
|
Задание:
Пусть А, В, С – деревья соответствующего типа, узлы которых могут содержать целочисленные значения. Требуется реализовать начальное формирование деревьев А и В, путем добавления некоторой последовательности значений (узлов) в пустое дерево. После чего требуется по варианту реализовать заданную операцию над деревьями без использования каких-либо вспомогательных структур (списков, массивов и т.п.), работая только с узлами деревьев А и В. Операция А=A ⋃пр B означает,что элементы дерева В будут добавлены в дерево А в прямом порядке обхода дерева В, соответственно А=A ⋃обр B – в обратном, а А=A ⋃сим B – симметричном обходе дерева В. Мой вариант:
Подскажите, как можно реализовать "список сыновей" на С++?
0
|
|
|
Комп_Оратор)
|
|
| 25.02.2019, 13:19 | |
|
Вот нашёл ссылочку:
http://bookwu.net/book_algorit... ya-derevev Вкратце могу сказать, что вижу такое в первые и... грустное оно. Идея ущербна с моей точки зрения, хотя скорее всего я её просто не понимаю. Фактически данная структура позволяет иметь доступ к одним и тем же узлам из нескольких (независимых!) ячеек списка. Суть в том, что все элементы заносятся в список. Вернее сказать - элементы списка содержащие пару указателей - один (ведущий) на узел дерева и один - на (ведомый) следующий узел. В списке присутствуют все узлы дерева в качестве ведущих . Каждый ведомый узел указывает на следующий нод в уровне следующем по отношению к ведущему в списке. Если таковых у нода дерева нет (лист) то в корневом списке у элемента с ведущим указателем на этот лист ведомый будет равен nullptr, то есть, грубо говоря - ноль. Это обозначено жирной точкой на схеме. То есть каждый ведомый указывает на следующий ведомый в этом же уровне слева-направо (в странах где читают и пишут слева направо) до конца. То есть последний в уровне тоже на ноль указывает. Bonttpol, глядя на это я могу перефразировать известное: Чем больше я узнаю математиков, тем больше люблю собак. (шутка, прошу математиков не обижаться. Тем более что все мы тут, включая и меня, грешного, немного того. Математики то есть. ).
1
|
|
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 25.02.2019, 14:18 [ТС] | |
|
Получается мне нужно писать структуру дерева. Потом писать список-в-списке, который хранит в перовом списке указатели на этот узел дерева и следующий, а второй список последовательность указателей на потомков?
0
|
|
|
Комп_Оратор)
|
||
| 25.02.2019, 14:58 | ||
Сообщение было отмечено Bonttpol как решение
РешениеBonttpol, можно использовать ноды вашего дерева. С точки зрения С++ это плохо (тоже мягко сказано), но задание есть задание. Например (не пишу и не компилирую, поэтому примите как идею) Вы создаёте std::list<Node> sones; вставляете корневой нод. создаёте пару итераторов std::list<Node>::iterator start_level, current_in_next_level; Инициализируете оба началом списка (сейчас там 1 нод - корневой нод всего дерева) Потом я бы организовал пару вложенных циклов. Наружный проходит по вставленным в предыдущем внутреннем. Внутренний на каждом вставляет в конец детей (если они есть) нодов полученных в наружном, По завершении наружного - обновляем итераторы начала и конца (на уже новый вставленный участок) или выходим если кончились элементы в дереве (тут счетчика хватит). Придётся чуток повозиться. То есть, для заполнения списка вы используете предыдущий уже вставленный накануне участок. Начальный участок начала всего действа, как я уже сказал, - один нод, - корневой нод дерева. Вроде красиво, но с моей точки зрения такая структура если её не защитить может принести дереву горе. Любая операция на дереве должна апдейтить список минимум в двух местах... Для практики - вполне сгодится. ![]() Добавлено через 9 минут И да. Это будет только список с не заполненными под списками. Назовём его корневым. Потом когда вы его получите придётся идти по нему и к каждому ноду вешать гирлянду следующего от него (как родителя) уровня. Эти ноды не будут копиями нодов дерева так как связаны они линейно и не в том порядке. То есть, каждый такой подсписок - развёрнутый в линию детский уровень нода в списке корневого уровня.
1
|
||
|
Комп_Оратор)
|
||||||
| 28.02.2019, 23:24 | ||||||
Сообщение было отмечено Bonttpol как решение
Решение
Bonttpol, вот дошли руки (шаловливые) до того чтобы написать как бы я сделал. Мотивом стало отсутствие в сети реализации списка сыновей на C++. Я не нашёл, во всяком разе.
Прошу не винить за реализацию дерева (там нет балансировки и всё очень примитивно). Я её нашёл в своих старых файлах и поскольку она что-то живое делает - использована для демонстрации. Если кто захочет переписать красиво - флаг в руки (булев). Bonttpol, в источнике, что я дал используются т.н. курсоры (указатель-заменители). Попытка это прочесть не увенчалась успехом и я решил сделать по-своему. Вообще, подумав я решил, что использовать сами по себе ноды как переменные это плохо. Нельзя вешать гирлянды разрушая связность самого дерева. То есть, напрашивается указатель указателя на нод. Это трудно читаемо и поскольку список то всё едино придётся использовать (std::list не писать же самому список) то в качестве связующего звена (дополнительного уровня) я решил использовать всё тот же список но на самих указателях Node. То есть корневой - list<list<Node*>> , а внутренние list<Node*> - "гирлянды" уровней каждого нода в корневом списке. В итоге, как я и предлагал, можно заполнять список обращаясь только его уже вставленным элементам. Пришлось пойти на святотатства вроде реализации конструктора копий для нода (чего не делают никогда), поэтому само дерево прошу не критиковать. Кто захочет - своё напишет.
2
|
||||||
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 01.03.2019, 13:50 [ТС] | |
|
Огромное спасибо. Только, почему то компилятор ругается на Ваш код. Мне пока починить не удалось.
0
|
|
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 01.03.2019, 14:48 [ТС] | |
|
0
|
|
|
Комп_Оратор)
|
||
| 01.03.2019, 16:40 | ||
|
Что касается ошибки то я посмотрел и выяснилось что на g++ это не компилится. Я пока не понял почему, но тупо заменил все list<list<Node*>>::const_iteratorгде сообщения о ошибке на auto и всё заработало. Вечером позже гляну, но может кто-то прольёт свет... Самому интересно, что ему не нравится.
0
|
||
|
Комп_Оратор)
|
||||||
| 02.03.2019, 00:19 | ||||||
|
Bonttpol, методом тыка выяснил что можно так:
1
|
||||||
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 05.03.2019, 09:17 [ТС] | |
|
IGPIGP, получается что Вы создаете стандартную структуру дерева, а в "список сыновей" , представленный массивом, записываете указатели на соответствующие узлы?
А можно ли после создания этого списка подчистить память и удаль дерево? Будут указатели после этого работать?
0
|
|
|
Комп_Оратор)
|
||||
| 05.03.2019, 09:46 | ||||
|
Bonttpol, я не совсем понял, если честно, что такое -Корневой список формировался суммированием уровней (а они сортированны в примере на сайте); -Корневой список создан из сортированной последовательности узлов, независимо от их расположения по уровням. Мне нравится 2-й вариант и вот почему. В случае если вы десериализуете дерево из потока, его конкретный вид будет зависеть от порядка следования данных. Это значит что на одном и том же наборе можно получать различные по составу уровней деревья. Тогда первый алгоритм будет "нестандартен" завися от конкретного размещения, а второй всегда будет один и тот же на заданном множестве данных. В целом, это глубоко философский вопрос и имеет больше значение для вашей головы, чем для вашей лабы. С чисто практической точки зрения, имеет смысл спросить у преподавателя, что ему представляется целесообразным. И сделать именно так. Для разугреву можете с ним слегка подискутировать использую полученные и осмысленные знания. Ему будет приятно (надеюсь). Вдобавок, хочу заметить, что сортированный корневой список созданный на базе lower_bound, что делает существование такого списка вполне осмысленным.Вначале я думал о возможности создания копии... но передумал. По выше озвученной причине. То есть, список - промежуточный уровень доступа к дереву (более высокого ранга). Без дерева он мёртв. Bonttpol, если я не прав, то реализовать копию, Вам не составит труда, имея то что мы тут раскопали.
1
|
||||
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 05.03.2019, 10:04 [ТС] | |
|
Большое Вам спасибо
1
|
|
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
||||||
| 05.03.2019, 14:08 [ТС] | ||||||
|
Я тут кое что переписала. И теперь мой список выглядит вот так:
1
|
||||||
|
Комп_Оратор)
|
||||||
| 05.03.2019, 14:55 | ||||||
0
|
||||||
|
4 / 4 / 0
Регистрация: 25.02.2019
Сообщений: 13
|
|
| 05.03.2019, 15:40 [ТС] | |
|
Мне кажется что этого списка достаточно. На том сайте же все сводилось к списку из связный списков. Тогда нужно делать связи между сыновьями (под "->" имеется ввиду указатель на брата):
1 [2]->[3] 2 [4]->[5] 3 [3]->[6] Скорее всего, это дополнительные указатели в структуре node. Боюсь, я это не потяну. А то что сейчас удалось реализовать я понимаю и могу объяснить.
1
|
|
| 05.03.2019, 15:40 | |
|
Помогаю со студенческими работами здесь
20
Деревья. Список сыновей
Реализация бинарного дерева поиска Реализация двоичного дерева поиска Реализация дерева цифрового поиска Искать еще темы с ответами Или воспользуйтесь поиском по форуму: |
|
Новые блоги и статьи
|
|||
|
http://iceja.net/ математические сервисы
iceja 20.01.2026
Обновила свой сайт http:/ / iceja. net/ , приделала Fast Fourier Transform экстраполяцию сигналов. Однако предсказывает далеко не каждый сигнал (см ограничения http:/ / iceja. net/ fourier/ docs ). Также. . .
|
http://iceja.net/ сервер решения полиномов
iceja 18.01.2026
Выкатила http:/ / iceja. net/ сервер решения полиномов (находит действительные корни полиномов методом Штурма).
На сайте документация по API, но скажу прямо VPS слабенький и 200 000 полиномов. . .
|
Расчёт переходных процессов в цепи постоянного тока
igorrr37 16.01.2026
/ *
Дана цепь постоянного тока с R, L, C, k(ключ), U, E, J. Программа составляет систему уравнений по 1 и 2 законам
Кирхгофа, решает её и находит переходные токи и напряжения на элементах схемы. . . .
|
Восстановить юзерскрипты Greasemonkey из бэкапа браузера
damix 15.01.2026
Если восстановить из бэкапа профиль Firefox после переустановки винды, то список юзерскриптов в Greasemonkey будет пустым.
Но восстановить их можно так.
Для этого понадобится консольная утилита. . .
|
|
Сукцессия микоризы: основная теория в виде двух уравнений.
anaschu 11.01.2026
https:/ / rutube. ru/ video/ 7a537f578d808e67a3c6fd818a44a5c4/
|
WordPad для Windows 11
Jel 10.01.2026
WordPad для Windows 11
— это приложение, которое восстанавливает классический текстовый редактор WordPad в операционной системе Windows 11. После того как Microsoft исключила WordPad из. . .
|
Classic Notepad for Windows 11
Jel 10.01.2026
Old Classic Notepad for Windows 11
Приложение для Windows 11, позволяющее пользователям вернуть классическую версию текстового редактора «Блокнот» из Windows 10. Программа предоставляет более. . .
|
Почему дизайн решает?
Neotwalker 09.01.2026
В современном мире, где конкуренция за внимание потребителя достигла пика, дизайн становится мощным инструментом для успеха бренда. Это не просто красивый внешний вид продукта или сайта — это. . .
|