#include<iostream>
using namespace std;
/*costruzione del tipo record chiamato nodo*/
typedef struct nodo
	{
	  int inf; //campo con informazione
	  nodo  *p; //campo puntatore interno alla lista
	  };
/*dichiarazione del puntatore di testa della lista ed assegnazione a NULL*/
nodo *testa=NULL;
/*inserimento di un nodo nella lista in coda */
void inserisci (nodo *&testa);//passaggio della testa by ref
/*stampa di tutta la lista */
void visualizza (nodo *testa);//passaggio della testa by val
/*cerca l'indirizzo di un valore dato in input*/
void ricerca (nodo *testa);//passaggio della testa by val
/*elimina un elemento dalla lista e dealloca lo spazio*/
void cancella (nodo *&testa);//passaggio della testa by ref

int main()
{

   int scelta ;
   do
   {

     cout<<"inserisci la scelta"<<endl;
     cout<<"1 per inserire"<<endl<<"2 per visualizzare "<<endl;
     cout<<"3 per ricercare"<<endl<<"4 per cancellare"<<endl;
     cout<<"5 per finire"<<endl;
     cin>>scelta;
     switch (scelta)
      {
	case 1:inserisci(testa); break;
	case 2:if (testa!=NULL) visualizza(testa); else cout<<"lista vuota"; break;
	case 3:if (testa!=NULL)ricerca(testa);else cout<<"lista vuota"<<endl;break;
	case 4:if (testa!=NULL) cancella(testa); else cout<<"lista vuota"<<endl;break;
     }
     }
	  while (scelta!=5);
  }

void inserisci(nodo *&testa)
    {
      /*se la testa è NULL inserisco in testa */          
      if (testa ==NULL)
      {
      testa=new nodo;
      cin>>testa->inf;
      testa->p=NULL;
          }
     /*per gli elementi successivi */
     else
     {
     /*uso un puntatore per scorrere la lista partendo dalla testa*/ 
      nodo *corr=testa;
      while(corr->p!=NULL)
      corr=corr->p;
      /*attivo un nuovo nodo nel campo puntatore dell'ultimo elemento */
      corr->p=new nodo;
      /*sposto corr sul nuovo nodo per leggere l'informazione */
      corr=corr->p;
      cin>>corr->inf;
      corr->p=NULL ;
      }
     }


void visualizza(nodo *testa)
     {
      nodo *corr=testa;
//scorro tutta la lista visualizzando il campo informativo
      while (corr!=NULL)
      {
    	cout<<corr->inf<<endl;
       corr=corr->p;
      }

  }
  void cancella(nodo *&testa)
     {
      nodo *corr=testa;
      int k;
      //inseriamo il avlore da cancellare
      cout<<"inserisci chiave di ricerca"<<endl;
      cin>>k;
      // se l'elemento è in testa modifichiamo il puntatore di testa
      if (testa->inf==k)
      {
          testa=testa->p;
          delete corr;}
       else
       //scorriamo la lista fino a trovare l'elemento da cancellare
       {
           nodo *prec=corr;              
      while (corr!=NULL && corr->inf!=k)
      {     prec=corr;
           corr=corr->p;
      }
      //se l'elemento è presente nella lista lo eliminiamo
        if (corr!=NULL)
         {
        prec->p=corr->p;
        delete corr;
        }
         else
         cout<<"elemento non presente"<<endl;
  }
}
  void ricerca(nodo *testa)
     {
      nodo *corr=testa;
      int k;
      cout<<"inserisci chiave di ricerca"<<endl;
      cin>>k;
      while (corr!=NULL && corr->inf!=k)
          {
           corr=corr->p;
           }
        if (corr!=NULL)
         cout<<"elemento presente nella locazione di memoria  "<<corr<<endl;
         else
         cout<<"elemento non presente"<<endl;
  }

