Zapis elementów listy jednokier. do drzewa BST.

0

Witam, mam problem z takim oto zadaniem(a raczej pewnym fragmentem). Program najpierw pobiera z pliku txt dane studenta z kolejnych wierszy następująco [pierwszy wiersz to liczba n - czyli liczba rekordów]:
n
nralbumu nazwisko imie grupa pkt
np.

3
29231 Dobry Tadek i4 20.5
12124 Niezla Iza i2 12.0
41012 Kiepski Gienek i2 4.4

Następnie zapisuje je do listy jednokierunkowej i wyświetla je na ekranie.
Do tego momentu wszystko mi śmiga, ale nie moge poradzić sobie z dalszym zagadnieniem.

Elementy listy chcę zapisać do drzewa BST, przy czym kolejne elementy lokowane są wg nr albumu. Następnie chciałbym odczytać metodą inorder posortowaną listę danych studentów.

oto mój kod, który co prawda się nie zawiesza, ale też nie zapisuje prawdopodobnie nic do drzewa, bo potem mi go nie wyświetla(nawet krzaków):

http://pastebin.com/LV9gbkUM

Bardzo proszę o pomoc jak to jest z tym transportowaniem do drzewa, bo czuję, że coś w podobie zadanie może pojawić się na zaliczeniu =))
Dziękuję z góry, pozdrawiam.

0

Stworz strukture/klase w ktorej kazdy obiekt bedzie zawieral wskaznik lewe i prawe dziecko. Nastepnie dodawaj ze wzgledu na nr albumu (mniejsze na lewo, wieksze na prawo). Odczytywanie jest nastepujace
5
2. 8

    1. 10
      
        1. 20
          Przechodzisz do najbardziej po lewej liscia i odczytujesz
          Odczyt_lewy(ojciec->lewy)
          Przy czym tutaj rekurencja wyglada tak, ze najpierw przechodzi do kolehnego lewego a dopiero pozniej wypisuje
          Odrazi pod tym
          Odczyt_prawy(ojciec->prawy) tutaj najpierw wypisanie a potem przejscie do nastepnego prawego
          Obie te funkcje umieszczasz w funkcji
          Odczyt(korzen)
          I wszystko dziala jak nalezy, posortowane ;]
0

no właśnie wydaje mi się,że tak ten pomysł opisałem :

struktury:

struct Tlista 

{

        int nr_albumu;

        float punkty;

        char grupa [5];

        char nazwisko [30];

        char imie [20];

        Tlista *next;

};

 

struct Twezel

{

        int nr_albumu;

        float punkty;

        char grupa [5];

        char nazwisko [30];

        char imie [20];

        Twezel *lewy;

        Twezel *prawy;

}; 
 void dodaj_wezel(struct Twezel *&wezel, struct Tlista *head)//dodawanie do drzewa

{

 

        if(wezel==NULL)

        {

                Twezel *wezel = new Twezel;

 

                wezel->nr_albumu = head->nr_albumu;

                wezel->punkty = head->punkty;

                strcpy(wezel->imie, head->imie);

                strcpy(wezel->nazwisko, head->nazwisko);

                strcpy(wezel->grupa, head->grupa);

 

 

                wezel->lewy = NULL;

                wezel->prawy = NULL;

        }

 

        else

                if(head->next->nr_albumu < wezel->nr_albumu)

                        dodaj_wezel(wezel->lewy, head->next);

                else

                        if(head->next->nr_albumu > wezel->nr_albumu)

                        dodaj_wezel(wezel->prawy, head->next);

 

}

odczyt drzewa inorder:

 void drukuj_drzewo(struct Twezel *korzen)

{

        if(korzen != NULL)

        {

        drukuj_drzewo(korzen->lewy);

        cout << korzen->nr_albumu << " " << korzen->nazwisko << " " << korzen->imie << " " <<korzen->grupa << " " << korzen->punkty << endl;

        drukuj_drzewo(korzen->prawy);

        }

}

no i program po odpaleniu zachowuje sie jakby w ogole nie zapisał do drzewa:/ cały kod: www.pastebin.com/LV9gbkUM

0

Wydaje mi się, że lista jest źle napisana a właściwie funkcja dodaj_wezel

0

wiem, właśnie proszę o zweryfikowanie tej części kodu. zmieniłem nazwę nowo tworzonego elementu oraz zmieniłem dodaj_wezel(wezel->lewy, head->next); na dodaj_wezel(wezel->lewy, head);, tak samo z prawym, ale to nic nie zmieniło ;/

0
rabston napisał(a)

Twezel *wezel = new Twezel;
To się nie skompiluje. Zmienna wezel już istnieje. Powinieneś użyć podanej referencji zamiast tworzyć nową zmienną lokalną.

rabston napisał(a)

if(head->next->nr_albumu < wezel->nr_albumu)

                    dodaj_wezel(wezel->lewy, head->next);

            else

                    if(head->next->nr_albumu > wezel->nr_albumu)

A co, gdy head->next->nr_albumu == wezel->nr_albumu ? Zamień < na <= lub zamień > na >=.

rabston napisał(a)

dodaj_wezel(wezel->lewy, head->next);
dlaczego przechodzisz do kolejnego elementu listy podczas przeszukiwania drzewa? Powinieneś po prostu wywołać dodaj_wezel dla każdego elementu listy:
for (item = head; item != NULL; item = item->next) dodaj_wezel(korzen, item);

Polecam jeszcze pewne zmiany. Deczko inny układ struktur:

struct Tdane
{
        int nr_albumu;
        float punkty;
        char grupa [5];
        char nazwisko [30];
        char imie [20];
};

struct Tlista : Tdane
{
        Tlista *next;
};

struct Twezel : Tdane {
        Twezel *lewy;
        Twezel *prawy;
};

void dodaj_wezel(struct Twezel *&wezel, struct Tdane *dane) // ...
0

Bardzo dziękuję za te cenne porady! Jak najbardziej zgadzam się z propozycjami!!

adf88 napisał(a)
rabston napisał(a)

Twezel *wezel = new Twezel;
To się nie skompiluje. Zmienna wezel już istnieje. Powinieneś użyć podanej referencji zamiast tworzyć nową zmienną lokalną.

 void dodaj_wezel(Twezel*& wezel, Tdane* dane)
{
	

		if(wezel == NULL)
		{
			Twezel* nw = new Twezel;
			nw->alb = dane->alb;
			nw->gr = dane->gr;
			nw->im = dane->im;
			nw->naz = dane->naz;
			nw->pkt = dane->pkt;
			nw->lewy = NULL;
			nw->prawy = NULL;

			wezel = nw;
		}
		else if(dane->alb < wezel->alb) dodaj(wezel->lewy, dane);

		else if(dane->alb > wezel->alb) dodaj(wezel->prawy, dane);
	
} 

tak o to uczyniłem

rabston napisał(a)

if(head->next->nr_albumu < wezel->nr_albumu)

                    dodaj_wezel(wezel->lewy, head->next);

            else

                    if(head->next->nr_albumu > wezel->nr_albumu)

A co, gdy head->next->nr_albumu == wezel->nr_albumu ? Zamień < na <= lub zamień > na >=.</quote>

co do tego, czy "head->next->nr_albumu" nie moze byc równy "wezel->nr_albumu" chciałbym dodać, że po 1)zakladamy unikalnosc numeru albumu 2) i tak cały rekord z takim wlasnie nrem albumu musiałby zostać pominięty, ze względu na metodę dodawania kolejnych elementów do drzewa BST[nowo dodawana mniejsza wartość na lewego syna,wieksza na prawo,a taka sama nie moze zostac dodana]

rabston napisał(a)

dodaj_wezel(wezel->lewy, head->next);
dlaczego przechodzisz do kolejnego elementu listy podczas przeszukiwania drzewa? Powinieneś po prostu wywołać dodaj_wezel dla każdego elementu listy:
for (item = head; item != NULL; item = item->next) dodaj_wezel(korzen, item);

</quote> racja, racja, świetny pomysł - też to dodałem.

I Śmiga jak złotoD stokrotne dzięki.
Ten pomysł z zapisem w inny sposób też jest bardzo ciekawy +zmiana argumentu z glowy listy na konkretną wartość..a wywoływane z maina dla każdego elementu listy.. nie wpadłbym na to za nic. Teraz jeszcze tylko pobawię się, tak, żeby ta PROCEDURA nie była wywoływana z maina, tylko zeby samowywołująca się rekurencyjna Funkcja, to mi pomoże lepiej zrozumieć inne możliwości robienia tego samego.
Bardzo dziękuję jeszcze raz i pozdrawiam!!

1 użytkowników online, w tym zalogowanych: 0, gości: 1