PDA

View Full Version : [c++]Visita di un albero binario ordinato


InformaticoRC
13-11-2011, 11:23
Salve
Dovrei implementare un programma che dato un albero binario ordinato,
lo visita in ampiezza(mediante coda) o profondità(mediante pila)
ho provato a scrivere il codice(prendendo in cosiderazione la visita in ampiezza, quindi mediante coda)

#include <iostream>
#include <stdlib.h>

using namespace std;

class albero
{
private:
int numero;
albero *sinistra;
albero *destra;

friend class coda;

public:
albero();
void set(int num) {numero=num;};
int get(){return numero;};
void pointsx(albero *point){sinistra=point;};
void pointdx(albero *point){destra=point;};
albero *getsx(){return sinistra;};
albero *getdx(){return destra;};
albero *inserisci(albero *temp, albero *nuovo);
void visualizza(albero *temp);
void BFS(albero *temp);
};

albero::albero()
{
numero=0;
sinistra=NULL;
destra=NULL;
}

albero *nuovo, *temp=NULL;

albero *albero::inserisci(albero *temp, albero *nuovo)
{
if(temp==NULL)
{
temp=nuovo;
}
else
{
if(nuovo->get() <= temp->get())
{
temp->pointsx(nuovo->inserisci(temp->getsx(), nuovo));
}
else
{
temp->pointdx(nuovo->inserisci(temp->getdx(), nuovo));
}
}
return (temp);
}

void albero::visualizza(albero *temp)
{
if(temp != NULL)
{
temp->visualizza(temp->getsx());
cout << temp->get() << " ";
temp->visualizza(temp->getdx());
}
}


void albero::BFS(albero *temp)
{
coda c ;
c.insert(temp);
while (!c.isEmpty())
{
temp=c.cancella();
while(temp!=NULL)
{c.insert(temp->getsx());
c.insert(temp->getdx());
}
}
}





///////////////////////

class coda
{
albero *temp;
albero *ultimo;
albero *nuovo;
coda c;


public:
coda()
{
temp=NULL;
ultimo=NULL;
nuovo=NULL;
}

void insert(albero *nodo)
{
nuovo=new albero;
cout << "inizializzo il nodo ";
nuovo->set(nodo->get());
cout <<temp->get();
if(temp==NULL)
{temp=nuovo;
ultimo=nuovo;}
else
{ultimo->pointsx(nuovo);
ultimo=nuovo;}
}

void cancella()
{
albero *del;
del=temp;
temp=temp->getdx();
temp=temp->getsx();
delete del;
}

albero *isEmpty()
{
if(temp==NULL)
{return NULL;}
else
{return temp;}
}
};





int main()
{
int scelta, num;

do
{
cout<<"\n";
cout<<"######################################################################\n";
cout<<"# ALBERO BINARIO ORDINATO #\n";
cout<<"######################################################################\n";
cout<<"# Digita 1 per inserire un numero #\n";
cout<<"# Digita 2 per visualizzare l'albero ordinato #\n";
cout<<"# Digita 3 per visitare l'albero in ampiezza #\n";
cout<<"######################################################################\n";
cout<<"\nDigita la tua scelta-->";
cin >> scelta;

switch(scelta)
{
case 1:
nuovo=new albero;
cout << "\nInserisci un numero -> ";
cin >> num;
nuovo->set(num);
temp = nuovo-> inserisci(temp, nuovo);
system ("pause");
system ("cls");
break;

case 2:
if(temp==NULL)
{
cout << "\nNon ci sono elementi nell'albero";
system ("pause");
system ("cls");
break;
}
else
{
cout << "\nL'albero ordinato: \n";
temp->visualizza(temp);
cout<< "\n";
system ("pause");
system ("cls");
break;
}
case 3:
temp->BFS(temp);
system ("pause");
system ("cls");
break;


default:
cout << "\nINSERISCI UN VALORE CORRETTO\n\n";
break;
}
}while(scelta != 4);
return 0;
}



scusate se è pasticciato o trovate errori banali ma con il lavoro su altri tanti programmi in c++ su tipi dati e strutture sto perdendo la testa, e mi resta soltanto questo programma funzionante per poter affrontare l'esame.
Il compilatore da un errore ( aggregate `coda c' has incomplete type and cannot be defined ), ma ci sarà sicuramente da modificare o aggiungere sicuramente più di una cosa(ad esempio nelle funzioni della classe coda di insert e cancella non so come far puntare temp al prossimo elemento indifferentemente che sia a sx o dx, visto che non ho metodi del tipo getnext(), pointto , ma ho getsx(),getdx(),pointsx,pointdx).
In questo programma oltre alla classe albero, ho la classe coda, ma avevo provato a fare uno anche con una classa nodo e 2 friend class: albero e coda, ma avevo troppi problemi con tipi variabili ecc
voi che dite?? :stordita:

Floris
13-11-2011, 15:52
Salve
Dovrei implementare un programma che dato un albero binario ordinato,
lo visita in ampiezza(mediante coda) o profondità(mediante pila)
ho provato a scrivere il codice(prendendo in cosiderazione la visita in ampiezza, quindi mediante coda)

Non ho letto il codice...ma perchè non farlo ricorsivo...così la "pila" la gestisce il compilatore?

InformaticoRC
13-11-2011, 16:28
Non ho letto il codice...ma perchè non farlo ricorsivo...così la "pila" la gestisce il compilatore?

vorrei farlo senza usare la ricorsione..
se dai un'occhiata al codice..che mi dici?

Floris
13-11-2011, 19:35
Ora non ho tempo! Ma se il problema è nelle definizioni di tipo allora prova a porre le definizioni delle funzioni membro della classe albero dopo la definizione della classe coda e le definizioni delle funzioni membro della classe coda dopo di queste...del tipo:

class albero {...
class coda {...
//definizioni funzioni della classe albero
//definizioni funzioni della classe coda

La soluzione migliore sarebbe però di separare dichiarazioni e definizioni in due file, uno .h (header) e l'altro .cpp.

InformaticoRC
15-11-2011, 16:54
Ora non ho tempo! Ma se il problema è nelle definizioni di tipo allora prova a porre le definizioni delle funzioni membro della classe albero dopo la definizione della classe coda e le definizioni delle funzioni membro della classe coda dopo di queste...del tipo:

class albero {...
class coda {...
//definizioni funzioni della classe albero
//definizioni funzioni della classe coda

La soluzione migliore sarebbe però di separare dichiarazioni e definizioni in due file, uno .h (header) e l'altro .cpp.


ho moficato il programma in questo modo:

#include <iostream>
#include <cstdlib>
using namespace std;

class albero
{
private:
int numero;
albero *sinistra;
albero *destra;
albero *prossimo;

friend class coda;

public:
albero();
void set(int num) {numero=num;};
int get(){return numero;};
void pointsx(albero *point){sinistra=point;};
void pointdx(albero *point){destra=point;};
albero *getsx(){return sinistra;};
albero *getdx(){return destra;};
void pointTo(albero *point){prossimo=point;}
albero *getnext(){return prossimo;}

albero *inserisci(albero *temp, albero *nuovo);
void visualizza(albero *temp);
void BFS(albero *temp);
};

class coda
{
albero *temp;
albero *ultimo;
albero *nuovo;



public:
coda();
void insert(albero *temp);
void cancella();
albero *isEmpty();
};

albero::albero()
{
numero=0;
sinistra=NULL;
destra=NULL;
}

albero *nuovo, *temp=NULL;

albero *albero::inserisci(albero *temp, albero *nuovo)
{
if(temp==NULL)
{
temp=nuovo;
}
else
{
if(nuovo->get() <= temp->get())
{
temp->pointsx(nuovo->inserisci(temp->getsx(), nuovo));
}
else
{
temp->pointdx(nuovo->inserisci(temp->getdx(), nuovo));
}
}
return (temp);
}

void albero::visualizza(albero *temp)
{
if(temp != NULL)
{
temp->visualizza(temp->getsx());
cout << temp->get() << " ";
temp->visualizza(temp->getdx());
}
}


void albero::BFS(albero *temp)
{
coda c ;
c.insert(temp);
while (c.isEmpty()!= NULL)
{
c.cancella();
if(temp!=NULL)
{c.insert(temp->getsx());
c.insert(temp->getdx());
}
}
}


coda::coda()
{
temp=NULL;
ultimo=NULL;
nuovo=NULL;
}

void coda::insert(albero *temp)
{
nuovo=new albero;
cout << "inizializzo il nodo ";
nuovo->set(temp->get());
cout <<temp->get();
if(temp==NULL)
{temp=nuovo;
ultimo=nuovo;}
else
{ultimo->pointTo(nuovo);
ultimo=nuovo;}

}

void coda::cancella()
{
albero *del;
del=nuovo;
temp=temp->getnext();
delete del;
}

albero *coda::isEmpty()
{
if(temp==NULL)
{return NULL;}
else
{return temp;}
}
int main()
{
int scelta, num;

do
{
cout<<"\n";
cout<<"######################################################################\n";
cout<<"# ALBERO BINARIO ORDINATO #\n";
cout<<"######################################################################\n";
cout<<"# Digita 1 per inserire un numero #\n";
cout<<"# Digita 2 per visualizzare l'albero ordinato #\n";
cout<<"# Digita 3 per visitare l'albero in ampiezza #\n";
cout<<"######################################################################\n";
cout<<"\nDigita la tua scelta-->";
cin >> scelta;

switch(scelta)
{
case 1:
nuovo=new albero;
cout << "\nInserisci un numero -> ";
cin >> num;
nuovo->set(num);
temp = nuovo-> inserisci(temp, nuovo);
system ("pause");
system ("cls");
break;

case 2:
if(temp==NULL)
{
cout << "\nNon ci sono elementi nell'albero";
system ("pause");
system ("cls");
break;
}
else
{
cout << "\nL'albero ordinato: \n";
temp->visualizza(temp);
cout<< "\n";
system ("pause");
system ("cls");
break;
}
case 3:
temp->BFS(temp);
system ("pause");
system ("cls");
break;


default:
cout << "\nINSERISCI UN VALORE CORRETTO\n\n";
break;
}
}while(scelta != 4);
return 0;
}




funziona, ma l'eseguibile si blocca nel momento in cui inizio la visita.
come mai?

Floris
15-11-2011, 17:47
Da errori? segmentation fault o roba simile? Il processo quando "si blocca" consuma CPU? continua a richiedere sempre più RAM?

InformaticoRC
15-11-2011, 18:04
Da errori? segmentation fault o roba simile? Il processo quando "si blocca" consuma CPU? continua a richiedere sempre più RAM?

si blocca l'eseguibile e dice che si è verificato un errore..
scusami se lo copi e incolli un secondo sul compilatore te ne renderai conto..
questo programma mi serve per domani e mi sta facendo udcire ormai
del tutto pazzooo :muro: :muro: :muro: :muro: