{ //Puntatori per accedere alla testa e alla coda della lista
Node<T> *front, *rear;
//Puntatori per le operaz. di Insert e Delete
Node<T> *prevPtr, *currPtr;
//Numero di item nella lista
int size;
//Posizione nella lista , usata da Reset
int position;
//Metodi privati per allocare e deallocare nodi
Node<T> *GetNode (const T& item, Node<T>* ptrNext=NULL);
void FreeNode (Node<T> *p);
//Copia lista L nella lista corrente
void CopyList (const LinkedList<T>& L);
public:
//Costruttori
LinkedList ();
LinkedList (const LinkedList<T>& L);
//Distruttore
~ LinkedList ();
//Operatore di assegnazione
LinkedList<T>& operator= (const LinkedList<T>& L);
//Metodi per verificare lo stato della lista
int ListSize () const;
int ListEmpty () const;
//Metodi per attraversare la lista
void Reset (int pos =0);
void Next ();
int EndOfList () const;
int CurrentPosition () const;
//Metodi per l'inserzione
void InsertFront (const T& item);
void InsertRear (const T& item);
void InsertAt (const T& item);
void InsertAfter (const T& item);
//Metodi per cancellare
T DeleteFront ();
void DeleteAt ();
//Modifica del contenuto informativo
T& Data ();
//Metodo per il clear della lista
void ClearList ();
//Metodo per dare Elemento alla testa
Node<T>* Front ();
};
//Implementazione della lista LinkedList
//Metodi privati
template <class T>
Node<T> *LinkedList<T>::GetNode(const T& item,
Node<T>* ptrNext)
{ Node<T> *p;
p = new Node<T>(item,ptrNext);
if (p == NULL)
{ cout << "Fallita allocazione memoria!\n";
exit(1);
}
return p;
}
template <class T>
void LinkedList<T>::FreeNode(Node<T> *p)
{ delete p;
}
// copia L nella lista corrente, che si assume vuota
template <class T>
void LinkedList<T>::CopyList(const LinkedList<T>& L)
{ Node<T> *p = L.front;
int pos;
// inserisce ogni Elemento in L in coda all'oggetto presente
while (p != NULL)
{ InsertRear(p->data);
p = p->NextNode();
} �
// se lista vuota return
if (position == -1)
return;
// reset prevPtr e currPtr nella nuova lista
prevPtr = NULL;
currPtr = front;
for (pos = 0; pos != position; pos++)
{ prevPtr = currPtr;
currPtr = currPtr->NextNode();
}
}
//Metodi pubblici
template <class T>
LinkedList<T>::LinkedList ():
front (NULL), rear (NULL), prevPtr (NULL),
currPtr (NULL), size (0), position (-1)
{}
template <class T>
LinkedList<T>::LinkedList(const LinkedList<T>& L)
{ front = rear = NULL;
prevPtr = currPtr = NULL;
size = 0;
position = -1;
CopyList(L);
}
template <class T>
void LinkedList<T>::ClearList()
{ Node<T> *currPosition, *nextPosition;
currPosition = front;
while(currPosition != NULL)
{ // indirizzo del nodo successivo e cancella il nodo corrente
nextPosition = currPosition->NextNode();
FreeNode(currPosition);
currPosition = nextPosition;
}
front = rear = NULL;
prevPtr = currPtr = NULL;
size = 0;
position = -1;
}
template <class T>
LinkedList<T>::~LinkedList()
{ ClearList();
}
template <class T>
LinkedList<T>& LinkedList<T>::operator=
(const LinkedList<T>& L)
{ � �
if (this == &L) //Non pu assegnare lista a s stessa
return *this;
ClearList();
CopyList(L);
return *this;
}
template <class T>
int LinkedList<T>::ListSize() const
{ return size;
}
template <class T>
int LinkedList<T>::ListEmpty() const
{ return size == 0;
}
// sposta avanti di un nodo prevPtr e currPtr
template <class T>
void LinkedList<T>::Next()
{ // se la scansione ha raggiunto la fine della lista o
�
// la lista vuota, return
if (currPtr != NULL)
{ // avanzano i due puntatori al nodo successivo
prevPtr = currPtr;
currPtr = currPtr->NextNode();
position++;
}
}
// True se il cliente ha attraversato la lista
template <class T>
int LinkedList<T>::EndOfList() const
{ return currPtr == NULL;
}
// restituisce la posizione del nodo corrente
template <class T>
int LinkedList<T>::CurrentPosition() const
{ return position;
}
//Reset per attraversare la lista a partire dall'inizio
template <class T>
void LinkedList<T>::Reset (int pos)
{ int startPos; �
//se la lista vuota return
if (front == NULL)
return; �
//se la posizione non valida terminare il programma
if (pos <0 || pos> size-1)
{ cerr << "Reset: posizione non valida: " << pos << endl;
return;
}
//Spostarsi sul nodo pos
if (pos ==0)
{ //reset alla testa lista
prevPtr = NULL;
currPtr = front;
position =0;
}
else
{ //Reset dei puntatori
currPtr = front->NextNode ();
prevPtr = front;
startPos = 1;
//Spostarsi fino a pos
for (position =startPos; position != pos; position++)
{ prevPtr = currPtr;
currPtr = currPtr->NextNode ();
}
}
}
// restituisce un reference al valore nel nodo corrente
template <class T>
T& LinkedList<T>::Data()
{ // errore se lista vota o scansione completa
if (size == 0 || currPtr == NULL)
{ cerr << "Data: reference non valida!" << endl;
exit(1);
}
return currPtr->data;
}
// Inserisce item alla testa di lista
template <class T>
void LinkedList<T>::InsertFront(const T& item)
{ �
// chiama Reset se la lista non vuota
if (front != NULL)
Reset();
InsertAt(item); // inserisce in testa
}
// Inserisce item in coda a lista
template <class T>
void LinkedList<T>::InsertRear(const T& item)
{ Node<T> *newNode;
prevPtr = rear;
newNode = GetNode(item); // crea il nuovo nodo
if (rear == NULL) // se lista vuota, inserisce in testa
front = rear = newNode;
else
{ rear->InsertAfter(newNode);
rear = newNode;
}
currPtr = rear;
position = size;
size++;
}
// Inserisce item in posizione corrente
template <class T>
void LinkedList<T>::InsertAt(const T& item)
{ Node<T> *newNode;
// 2 casi: inserzione in testa o dentro la lista
if (prevPtr == NULL)
{ // inserisce in testa,
// pone nodo in una lista vuota
newNode = GetNode(item,front);
front = newNode;
}
else
{ // inserisce in lista, pone il nodo dopo prevPtr
newNode = GetNode(item);
prevPtr->InsertAfter(newNode);
}
// if prevPtr == rear, si sta inserendo in lista vuota
// o in coda di una lista non vuota; aggiorna rear e position
if (prevPtr == rear)
{ rear = newNode;
position = size;
}
// aggiorna currPtr e incrementa size
currPtr = newNode;
size++;
}
// Inserisce item dopo la posizione corrente
template <class T>
void LinkedList<T>::InsertAfter(const T& item)
{ Node<T> *p;
p = GetNode(item);
if (front == NULL) // inserzione in lista vuota
{ front = currPtr = rear = p;
position = 0;
}
else
{ // inserzione dopo l'ultimo nodo
if (currPtr == NULL)
currPtr = prevPtr;
currPtr->InsertAfter(p);
if (currPtr == rear)
{ rear = p;
position = size;
}
else position++;
prevPtr = currPtr;
currPtr = p;
}
size++; // incrementa size
}
// Cancella nodo in testa
template <class T>
T LinkedList<T>::DeleteFront()
{ T item;
Reset();
if (front == NULL)
{ cerr << "Cancellazione non valida!" << endl;
exit(1);
}
item = currPtr->data;
DeleteAt();
return item;
}
//Cancella nodo in posizione corrente
template <class T>
void LinkedList<T>::DeleteAt()
{ Node<T> *p;
// error se lista vuota o fine lista
if (currPtr == NULL)
{ cerr << "Cancellazione non valida!" << endl;
exit(1);
}
// cancella zione in testa o dentro
if (prevPtr == NULL)
{ // salva l'indirizzo della testa
�
// se ultimo nodo front diventa NULL
p = front;
front = front->NextNode();
}
else // scollega nodo dopo prevPtr, salva indirizzo
p = prevPtr->DeleteAfter();
� �
// se rear cancellato, nuova rear prevPtr e position
� �
// decrementata; altrimenti, position la stessa
// se p era ultimo nodo, rear = NULL e position = -1
if (p == rear)
{ rear = prevPtr;
position--;
} �
// sposta currPtr dopo il nodo cancellato, se p ultimo nodo
//currPtr diventa NULL
currPtr = p->NextNode();
// rilascia il nodo e decrementa size
cout<< "Cancellare in llist"<<endl;
FreeNode(p);
size--;
}
template <class T>
Node<T>* LinkedList<T>::Front ( )
{ return front;
}
// CLASSE SEQLIST
template <class T>
class SeqListIterator;
template <class T>
class SeqList: public List<T>
{ protected:
// oggetto lista linkata
LinkedList<T> llist;
public:
// costruttore
SeqList();
// metodi di accesso alla lista
virtual int Find (T& item);
T GetData(int pos);
// Metodi di modifica della lista
virtual void Insert(const T& item);
virtual void Delete(const T& item);
T DeleteFront( );
virtual void ClearList( );
// SeqListIterator richiede di accedere a llist
friend class SeqListIterator<T>;
};
// costruttore di default inizializza classe base
template <class T>
SeqList<T>::SeqList(): List<T>()
{}
// usa metodo ClearList per il clear di llist
template <class T>
void SeqList<T>::ClearList()
{ llist.ClearList();
size = 0;
}
// usa metodo InsertRear per aggiungere Elementi in coda alla lista
template <class T>
void SeqList<T>::Insert(const T& item)
{ llist.InsertRear(item);
size++; // aggiorna size
}
// usa metodo DeleteFront per rimuovere il I Elemento
template <class T>
T SeqList<T>::DeleteFront()
{ size--;
return llist.DeleteFront();
} �
// cancella nodo il cui valore uguale ad item
template <class T>
void SeqList<T>::Delete(const T& item)
{ int result = 0;
// ricerca item se trova, pone result a true
for(llist.Reset();!llist.EndOfList();llist.Next())
if (item == llist.Data())
{ result++;
break;
}
// se ha trovato item, lo cancella e decrementa size
if (result)
{ cout<<"cancellare"<<endl;
llist.DeleteAt();
size--;
}
}
// restituisce il valore di item nella posizione pos
template <class T>
T SeqList<T>::GetData(int pos)
�
{ // verifica se posizione valida
if (pos < 0 || pos >= llist.ListSize())
{ �
cerr << "pos fuori range!" << endl;
exit(1);
}
// pone a pos posizione corrente nella linked list e return data
llist.Reset(pos);
return llist.Data();
}
// Ricerca item in lista, return True se trova
// False altrimenti. Se ha trovato
// assegna l'Elemento al parametro reference item
template <class T>
int SeqList<T>::Find (T& item)
{ int result = 0;
// ricerca item in lista, se trova, set result a True
for(llist.Reset();!llist.EndOfList();llist.Next())
if (item == llist.Data())
{ result++;
break;
}
// se True, aggiorna item e return True; else, return False
if (result)
item = llist.Data();
return result;
}
//CLASSE SEQLISTITERATOR DERIVATA DA ITERATOR
template <class T>
class SeqListIterator: public Iterator<T>
{ private:
// puntatore locale a SeqList che si sta scandendo
SeqList<T> *listPtr;
// mantiene puntatori previous e current
// mentre si scandisce la lista
Node<T> *prevPtr, *currPtr;
public:
// costruttore
SeqListIterator(SeqList<T>& lst);
// Metodi per la scansione
virtual void Next();
virtual void Reset();
// Metodi per accedere e modificare il dato
virtual T& Data();
// fa il reset dell'iteratore per scandire una nuova lista
�
// l'equivalente del costruttore in run time
void SetList(SeqList<T>& lst);
};
// costruttore: inizializza costruttore classe base e puntatore SeqList
template <class T>
SeqListIterator<T>::SeqListIterator(SeqList<T>& lst) :
Iterator<T>(), listPtr(&lst)
{ �
// La lista pu essere vuota
iterationComplete = listPtr->llist.ListEmpty();
// posiziona iterator al front della lista
Reset();
}
// avanza al successivo Elemento di lista �
//quando arriva alla fine lista segnala che l'iterazione completa
template <class T>
void SeqListIterator<T>::Next()
{ � �
//se currPtr NULL, si alla fine di lista
if (currPtr == NULL)
return;
// si sposta prevPtr/currPtr avanti di un nodo
prevPtr = currPtr;
currPtr = currPtr->NextNode();
�
// se si alla fine della lista, segnala
�
// che l'iterazione completa
if (currPtr == NULL)
iterationComplete = 1;
}
// Inizializza la scansione all'inizio di lista
template <class T>
void SeqListIterator<T>::Reset()
{ // riasssegna lo stato della iteratione
iterationComplete = listPtr->llist.ListEmpty();
�
// se lista vuota, return
if (listPtr->llist.Front() == NULL)
return;
// inizializza al primo nodo della lista
prevPtr = NULL;
currPtr = listPtr->llist.Front();
}
// restituisce il valore del nodo corrente nella lista
template <class T>
T& SeqListIterator<T>::Data()
{ �
// errore se lista vuota o scansione completa
if (listPtr->llist.ListEmpty() || currPtr == NULL)
{ cerr << "Data: riferimento non valido!" << endl;
exit(1);
}
return currPtr->data;
}
//L'iteratore attraversa una nuova lista lst passata come parametro,
//riassegna listPtr e chiama Reset
template <class T>
void SeqListIterator<T>::SetList(SeqList<T>& lst)
{ listPtr = &lst;
// posiziona al primo dato nella nuova lista
Reset();
}
//**********************Classe Date *************************************
class Date
{ //dati membro (giorno, mese, anno)
short int gg;
short int mm;
int aa;
public:
//costruttori e distruttori
Date() {gg=1;mm=1;aa=1999;};
Date(short int, short int, int);
~Date() {gg=mm=aa=0;};
//metodi
short int GetG() {return gg;}
Scarica il documento per vederlo tutto.
Scarica il documento per vederlo tutto.
Scarica il documento per vederlo tutto.
Scarica il documento per vederlo tutto.
Programma molto lungo che riprende diversi esempi di classe e si basa sulla teoria dell'ereditarietà ,polimorfismo e sturutture varie.