algoritmi e programmazione avanzata - liste, pile, code

Post on 14-Jun-2015

174 Views

Category:

Education

3 Downloads

Preview:

Click to see full reader

DESCRIPTION

Argomenti trattati: - gestione di uno stack con liste concatenate - queue con liste concatenate - liste concatenate ordinate

TRANSCRIPT

stack.c

/*

Algoritmi e Programmazione Avanzata

Tutore: Sergio Porcu

Argomento: stack

Gestione di uno stack con liste concatenate

*/

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

#define MAX_STR 10

/* Utilizzo costanti locali invece di

EXIT_SUCCESS e EXIT_FAILURE */

#define SUCCESS 1

#define FAILURE 0

struct e {

int key;

/* ... altri eventuali campi dato ... */

struct e *next;

};

struct e *push (struct e *pTop, int val);

struct e *pop (struct e *pTop, int *val, int *status);

struct e *newE ( );

void traversal (struct e *pTop);

void lettura (int *val);

void stampa (int val, int status);

int

main (

void

)

{

char scelta[MAX_STR];

struct e *pTop;

int val, status;

pTop = NULL;

do {

printf (

"Effettua la scelta (push (p), pop (o), traversal (t), f (fine)): ");

scanf ("%s", scelta);

if (strcmp (scelta, "p") == 0) {

lettura (&val);

pTop = push (pTop, val);

} else

if (strcmp (scelta, "o") == 0) {

pTop = pop (pTop, &val, &status);

stampa (val, status);

} else {

-1-

stack.c

if (strcmp (scelta, "t") == 0) {

traversal (pTop);

} else {

if (strcmp (scelta, "f") != 0) {

printf ("Scelta errata!!!\n");

}

}

}

} while (strcmp (scelta, "f") != 0);

return (SUCCESS);

}

struct e *

push (

struct e *pTop,

int val

)

{

struct e *pNew;

pNew = newE ();

pNew->key = val;

pNew->next = pTop;

pTop = pNew;

return (pTop);

}

struct e *

pop (

struct e *pTop,

int *val,

int *status

)

{

struct e *pOld;

if (pTop != NULL) {

*status = SUCCESS;

*val = pTop->key;

pOld = pTop;

pTop = pTop->next;

free (pOld);

} else {

*status = FAILURE;

}

return (pTop);

}

void

traversal (

struct e *pTop

)

{

-2-

stack.c

struct e *pTmp;

fprintf (stdout, "pTop -> ");

pTmp = pTop;

while (pTmp != NULL) {

fprintf (stdout, "%d -> ", pTmp->key);

pTmp = pTmp->next;

}

fprintf (stdout, "NULL \n");

return;

}

struct e *

newE (

)

{

struct e *ePtr;

ePtr = (struct e *) malloc (sizeof (struct e));

if (ePtr==NULL) {

fprintf (stderr, "Allocazione fallita.");

exit (FAILURE);

}

return (ePtr);

}

/* lettura dati */

void

lettura (

int *val

)

{

fprintf (stdout, "Elemento da introdurre = ");

scanf ("%d", val);

return;

}

/* visualizzazione dati */

void

stampa (

int val,

int status

)

{

if (status == SUCCESS) {

fprintf (stdout, "Elemento estratto = %d\n", val);

} else {

fprintf (stdout, "Elemento inesistente.\n");

}

return;

}

-3-

stack.c

-4-

queue.c

/*

Algoritmi e Programmazione Avanzata

Tutore: Sergio Porcu

Argomento: queue

Queue con liste concatenate

*/

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

#define MAX_STR 10

#define SUCCESS 2

#define FAILURE 3

struct e {

int key;

/* ... */

struct e *next;

};

struct e *enqueue (struct e *pTail, int val);

struct e *dequeue (struct e *pTail, int *val, int *status);

struct e *newE ( );

void traversal (struct e *pTail);

void lettura (int *val);

void stampa (int val, int status);

int

main (

void

)

{

char scelta[MAX_STR];

struct e *pTail;

int val, status;

pTail = NULL;

do {

printf (

"Effettua la scelta (enqueue (e), dequeue (d), traversal (t),"

" f (fine)): ");

scanf ("%s", scelta);

if (strcmp (scelta, "e") == 0) {

lettura (&val);

pTail = enqueue (pTail, val);

} else

if (strcmp (scelta, "d") == 0) {

pTail = dequeue (pTail, &val, &status);

stampa (val, status);

} else {

if (strcmp (scelta, "t") == 0) {

-1-

queue.c

traversal (pTail);

} else {

if (strcmp (scelta, "f") != 0) {

printf ("Scelta errata!!!\n");

}

}

}

} while (strcmp (scelta, "f") != 0);

return (SUCCESS);

}

struct e *

enqueue (

struct e *pTail,

int val

)

{

struct e *pNew;

pNew = newE ();

pNew->key = val;

/* campi */

if (pTail==NULL) {

pTail = pNew;

pTail->next = pTail;

} else {

pNew->next = pTail->next;

pTail->next = pNew;

pTail = pNew;

}

return (pTail);

}

struct e *

dequeue (

struct e *pTail,

int *val,

int *status

)

{

struct e *pOld;

if (pTail != NULL) {

*status = SUCCESS;

if (pTail == pTail->next) {

*val = pTail->key;

free (pTail);

pTail = NULL;

} else {

pOld = pTail->next;

*val = pOld->key;

pTail->next = pOld->next;

free (pOld);

-2-

queue.c

}

} else {

*status = FAILURE;

}

return (pTail);

}

void

traversal (

struct e *pTail

)

{

struct e *pTmp;

fprintf (stdout, "pTail -> ");

if (pTail == NULL) {

fprintf (stdout, "NULL\n");

} else {

pTmp = pTail;

do {

fprintf (stdout, "%d -> ", pTmp->key);

pTmp = pTmp->next;

} while (pTmp != pTail);

fprintf (stdout, "pTail \n");

}

return;

}

struct e *

newE (

)

{

struct e *p;

p = (struct e *) malloc (sizeof (struct e));

if (p==NULL) {

fprintf (stderr, "Allocazione fallita.");

exit (FAILURE);

}

return (p);

}

/* lettura dati */

void

lettura (

int *val

)

{

fprintf (stdout, "Elemento da introdurre = ");

scanf ("%d", val);

return;

-3-

queue.c

}

/* visualizzazione dati */

void

stampa (

int val,

int status

)

{

if (status == SUCCESS) {

fprintf (stdout, "Elemento estratto = %d\n", val);

} else {

fprintf (stdout, "Elemento inesistente.\n");

}

return;

}

-4-

listOfInt.c

/*

Algoritmi e Programmazione Avanzata

Tutore: Sergio Porcu

Argomento: liste concatenate ordinate

Gestione tramite menu e doppio puntatore. Dati i nteri.

*/

#include <stdio.h>

#include <stdlib.h>

#include <ctype.h>

/************************************************** ******************

DEFINIZIONE DATI

*************************************************** *****************/

#define MAXC 30

#define SUCCESS 2

#define FAILURE 3

typedef int dato_t ;

typedef struct nodo {

dato_t val ;

struct nodo *punt ;

} nodo_t ;

/************************************************** ******************

PROTOTIPI

*************************************************** *****************/

/* Gestione Dati */

dato_t leggiDato (FILE *fp );

void stampaDato (FILE *fp , dato_t dato );

int precede (dato_t d1 , dato_t d2 );

int uguali (dato_t d1 , dato_t d2 );

/* Gestione Lista */

nodo_t *myAlloc (void );

nodo_t *creaListaVuota (void );

nodo_t *inserisci (nodo_t *hp, dato_t dato );

void stampaLista (FILE *fp , nodo_t *hp);

int cerca (nodo_t *hp, dato_t dato );

nodo_t *cancella (nodo_t *hp, dato_t dato );

nodo_t *leggiLista (FILE *fp );

/************************************************** ******************

GETIONE DATI

(sezione che puo' rendere il programma indipendent e dal tipo

di dati, e.g., funzionamento con stringhe di carat teri)

*************************************************** *****************/

dato_t

leggiDato (

FILE *fp

)

-1-

listOfInt.c

{

dato_t dato ;

/* Solo nel caso di fp==stdin visualizzo una richie sta-utente */

if (fp ==stdin ) {

fprintf (stdout , "Valore (intero): " );

}

fscanf (fp , "%d" , &dato );

return (dato );

}

void

stampaDato (

FILE *fp ,

dato_t dato

)

{

fprintf (fp , "%d\n" , dato );

return;

}

int

precede (

dato_t d1 ,

dato_t d2

)

{

if (d1 < d2)

return (1);

else

return (0);

}

int

uguali (

dato_t d1 ,

dato_t d2

)

{

if (d1 == d2)

return (1);

else

return (0);

}

/************************************************** ******************

GESTIONE LISTA

*************************************************** *****************/

nodo_t

*creaListaVuota (

void

)

{

-2-

listOfInt.c

return (NULL);

}

int

cerca (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p;

for (p = hp; (p != NULL)&&(precede (p->val , dato )); p = p->punt );

if ((p != NULL)&&(uguali (p->val , dato )))

return (1);

else

return (0);

}

nodo_t

*cancella (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p, *q0, *q1;

/* Lista vuota */

if (hp == NULL) {

fprintf (stderr , "ATTENZIONE: dato inesistente\n" );

return (hp);

}

/* Cancella in testa */

if (uguali (dato , hp->val )) {

p = hp->punt ;

free (hp);

return (p);

}

/* Cancella in mezzo o in coda. Percorrimento con d oppio puntatore:

q0 e q1 puntano a due nodi consecutivi, al mom ento dell'inserimento

q0 punta al nodo precedente, q1 al nodo da can cellare

*/

q0 = hp; q1 = hp->punt ;

/* cerca posizione - eventualmente fine lista (q1 = = NULL) */

while ((q1 != NULL)&&(precede (q1->val , dato ))) {

q0 = q1;

q1 = q1->punt ;

}

if ((q1 != NULL)&&(uguali (q1->val , dato ))) {

/* cancella */

q0->punt = q1->punt ;

free (q1);

}

else

fprintf (stderr , "ATTENZIONE: dato inesistente\n" );

-3-

listOfInt.c

/* hp non viene modificato */

return (hp);

}

nodo_t

*inserisci (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p, *q0, *q1;

p = myAlloc ();

p->val = dato ;

/* Lista vuota */

if (hp == NULL) {

p->punt = NULL;

return (p);

}

/* Inserimento in testa */

if (precede (dato , hp->val )) {

p->punt = hp;

return (p);

}

/* Inserimento in mezzo o in coda. Percorrimento co n doppio puntatore:

q0 e q1 puntano a due nodi consecutivi, al mom ento dell'inserimento

q0 punta al nodo precedente, q1 al successivo

*/

q0 = hp; q1 = hp->punt ;

/* cerca posizione - eventualmente fine lista (q1 = = NULL) */

while ((q1 != NULL)&&(precede (q1->val , dato ))) {

q0 = q1;

q1 = q1->punt ;

}

/* inserisce */

q0->punt = p;

p->punt = q1;

/* hp non viene modificato */

return (hp);

}

void

stampaLista (

FILE *fp ,

nodo_t *hp

)

{

fprintf (stdout , "Lista:\n" );

while (hp != NULL) {

stampaDato (fp , hp->val );

hp = hp->punt ;

}

}

-4-

listOfInt.c

nodo_t

*leggiLista (

FILE *fp

)

{

nodo_t *p, *hp, *tp ;

dato_t d ;

hp = tp = NULL;

while (!feof (fp )) {

/* acquisisci dato */

d = leggiDato (fp );

p = myAlloc ();

p->val = d;

p->punt = NULL;

/* inserisci in coda */

if (tp == NULL)

hp = tp = p;

else {

tp ->punt = p;

tp = p;

}

}

return (hp);

}

nodo_t

*myAlloc (

void

)

{

nodo_t *p;

p = (nodo_t *) malloc (sizeof (nodo_t ));

if (p == NULL) {

fprintf (stderr , "ERRORE: memoria dinamica insufficiente\n" );

exit (1);

}

return (p);

}

/************************************************** ******************

MAIN

*************************************************** *****************/

int

main (

void

)

{

nodo_t *headp ;

-5-

listOfInt.c

dato_t d ;

int fine = 0;

char riga [MAXC];

FILE *fp ;

headp = creaListaVuota ();

while (!fine ) {

fprintf (stdout ,

"(I)ns/(R)ic/(C)anc/(V)isualizza/(S)alva/(L)eggi/(F )ine : " );

scanf ("%s" , riga );

switch (tolower (riga [0])) {

case 'c' :

d = leggiDato (stdin );

headp = cancella (headp , d);

break;

case 'f' :

fine = 1;

break;

case 'i' :

d = leggiDato (stdin );

headp = inserisci (headp , d);

break;

case 'l' :

fprintf (stdout , "Nome file: " );

scanf ("%s" , riga );

fp = fopen (riga , "r" );

if (fp == NULL) {

fprintf (stderr , "ERRORE in apertura di %s\n" , riga );

} else {

headp = leggiLista (fp );

}

break;

case 'r' :

d = leggiDato (stdin );

if (cerca (headp , d) == 1)

fprintf (stdout , "Trovato\n" );

else

fprintf (stdout , "Non trovato\n" );

break;

case 's' :

fprintf (stdout , "Nome file: " );

scanf ("%s" , riga );

fp = fopen (riga , "w" );

if (fp == NULL) {

fprintf (stderr , "ERRORE in apertura di %s\n" , riga );

}

else {

stampaLista (fp , headp );

fclose (fp );

}

break;

case 'v' :

stampaLista (stdout , headp );

break;

-6-

listOfInt.c

default:

fprintf (stderr , "Opzione sconosciuta\n" );

}

}

return (SUCCESS);

}

-7-

listOfString.c

/*

Algoritmi e Programmazione Avanzata

Tutore: Sergio Porcu

Argomento: liste concatenate ordinate

Gestione tramite menu e doppio puntatore.

Dati stringhe di caratteri.

Si osservi come questo programma sia stato

ottenuto dal programma

denominato listOfInt.c mediante modifica della

sola sezione "DATI" per modificare una lista

di interi in una di stringhe.

*/

#include <stdio.h>

#include <string.h>

#include <stdlib.h>

#include <ctype.h>

/************************************************** ******************

DEFINIZIONE DATI

*************************************************** *****************/

#define MAXC 30

#define SUCCESS 2

#define FAILURE 3

typedef char * dato_t ;

typedef struct nodo {

dato_t val ;

struct nodo *punt ;

} nodo_t ;

/************************************************** ******************

PROTOTIPI

*************************************************** *****************/

/* Gestione Dati */

dato_t leggiDato (FILE *fp );

void stampaDato (FILE *fp , dato_t dato );

int precede (dato_t d1 , dato_t d2 );

int uguali (dato_t d1 , dato_t d2 );

/* Gestione Lista */

nodo_t *myAlloc (void );

nodo_t *creaListaVuota (void );

nodo_t *inserisci (nodo_t *hp, dato_t dato );

void stampaLista (FILE *fp , nodo_t *hp);

int cerca (nodo_t *hp, dato_t dato );

nodo_t *cancella (nodo_t *hp, dato_t dato );

nodo_t *leggiLista (FILE *fp );

/************************************************** ******************

GETIONE DATI

(sezione che puo' rendere il programma indipendent e dal tipo

-1-

listOfString.c

di dati, e.g., funzionamento con stringhe di carat teri)

*************************************************** *****************/

dato_t

leggiDato (

FILE *fp

)

{

char tmpDato [MAXC];

dato_t dato ;

/* Solo nel caso di fp==stdin visualizzo una richie sta-utente */

if (fp ==stdin ) {

fprintf (stdout , "Valore (stringa di caratteri): " );

}

fscanf (fp , "%s" , tmpDato );

dato = (char *) malloc ((strlen (tmpDato ) + 1) * sizeof (char ));

if (dato == NULL) {

fprintf (stderr , "ERRORE: memoria dinamica insufficiente.\n" );

exit (1);

}

strcpy (dato , tmpDato );

return (dato );

}

void

stampaDato (

FILE *fp ,

dato_t dato

)

{

fprintf (fp , "%s\n" , dato );

return;

}

int

precede (

dato_t d1 ,

dato_t d2

)

{

if (strcmp (d1, d2) < 0)

return (1);

else

return (0);

}

int

uguali (

dato_t d1 ,

dato_t d2

)

{

-2-

listOfString.c

if (strcmp (d1, d2) == 0)

return (1);

else

return (0);

}

/************************************************** ******************

GESTIONE LISTA

*************************************************** *****************/

nodo_t

*creaListaVuota (

void

)

{

return (NULL);

}

int

cerca (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p;

for (p = hp; (p != NULL)&&(precede (p->val , dato )); p = p->punt );

if ((p != NULL)&&(uguali (p->val , dato )))

return (1);

else

return (0);

}

nodo_t

*cancella (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p, *q0, *q1;

/* Lista vuota */

if (hp == NULL) {

fprintf (stderr , "ATTENZIONE: dato inesistente\n" );

return (hp);

}

/* Cancella in testa */

if (uguali (dato , hp->val )) {

p = hp->punt ;

free (hp);

return (p);

}

/* Cancella in mezzo o in coda. Percorrimento con d oppio puntatore:

q0 e q1 puntano a due nodi consecutivi, al mom ento dell'inserimento

q0 punta al nodo precedente, q1 al nodo da can cellare

-3-

listOfString.c

*/

q0 = hp; q1 = hp->punt ;

/* cerca posizione - eventualmente fine lista (q1 = = NULL) */

while ((q1 != NULL)&&(precede (q1->val , dato ))) {

q0 = q1;

q1 = q1->punt ;

}

if ((q1 != NULL)&&(uguali (q1->val , dato ))) {

/* cancella */

q0->punt = q1->punt ;

free (q1);

}

else

fprintf (stderr , "ATTENZIONE: dato inesistente\n" );

/* hp non viene modificato */

return (hp);

}

nodo_t

*inserisci (

nodo_t *hp,

dato_t dato

)

{

nodo_t *p, *q0, *q1;

p = myAlloc ();

p->val = dato ;

/* Lista vuota */

if (hp == NULL) {

p->punt = NULL;

return (p);

}

/* Inserimento in testa */

if (precede (dato , hp->val )) {

p->punt = hp;

return (p);

}

/* Inserimento in mezzo o in coda. Percorrimento co n doppio puntatore:

q0 e q1 puntano a due nodi consecutivi, al mom ento dell'inserimento

q0 punta al nodo precedente, q1 al successivo

*/

q0 = hp; q1 = hp->punt ;

/* cerca posizione - eventualmente fine lista (q1 = = NULL) */

while ((q1 != NULL)&&(precede (q1->val , dato ))) {

q0 = q1;

q1 = q1->punt ;

}

/* inserisce */

q0->punt = p;

p->punt = q1;

/* hp non viene modificato */

return (hp);

}

-4-

listOfString.c

void

stampaLista (

FILE *fp ,

nodo_t *hp

)

{

fprintf (stdout , "Lista:\n" );

while (hp != NULL) {

stampaDato (fp , hp->val );

hp = hp->punt ;

}

}

nodo_t

*leggiLista (

FILE *fp

)

{

nodo_t *p, *hp, *tp ;

dato_t d ;

hp = tp = NULL;

while (!feof (fp )) {

/* acquisisci dato */

d = leggiDato (fp );

p = myAlloc ();

p->val = d;

p->punt = NULL;

/* inserisci in coda */

if (tp == NULL)

hp = tp = p;

else {

tp ->punt = p;

tp = p;

}

}

return (hp);

}

nodo_t

*myAlloc (

void

)

{

nodo_t *p;

p = (nodo_t *) malloc (sizeof (nodo_t ));

if (p == NULL) {

fprintf (stderr , "ERRORE: memoria dinamica insufficiente\n" );

exit (1);

-5-

listOfString.c

}

return (p);

}

/************************************************** ******************

MAIN

*************************************************** *****************/

int

main (

void

)

{

nodo_t *headp ;

dato_t d ;

int fine = 0;

char riga [MAXC];

FILE *fp ;

headp = creaListaVuota ();

while (!fine ) {

fprintf (stdout ,

"(I)ns/(R)ic/(C)anc/(V)isualizza/(S)alva/(L)eggi/(F )ine : " );

scanf ("%s" , riga );

switch (tolower (riga [0])) {

case 'c' :

d = leggiDato (stdin );

headp = cancella (headp , d);

break;

case 'f' :

fine = 1;

break;

case 'i' :

d = leggiDato (stdin );

headp = inserisci (headp , d);

break;

case 'l' :

fprintf (stdout , "Nome file: " );

scanf ("%s" , riga );

fp = fopen (riga , "r" );

if (fp == NULL) {

fprintf (stderr , "ERRORE in apertura di %s\n" , riga );

} else {

headp = leggiLista (fp );

}

break;

case 'r' :

d = leggiDato (stdin );

if (cerca (headp , d) == 1)

fprintf (stdout , "Trovato\n" );

else

fprintf (stdout , "Non trovato\n" );

break;

-6-

listOfString.c

case 's' :

fprintf (stdout , "Nome file: " );

scanf ("%s" , riga );

fp = fopen (riga , "w" );

if (fp == NULL) {

fprintf (stderr , "ERRORE in apertura di %s\n" , riga );

}

else {

stampaLista (fp , headp );

fclose (fp );

}

break;

case 'v' :

stampaLista (stdout , headp );

break;

default:

fprintf (stderr , "Opzione sconosciuta\n" );

}

}

return (SUCCESS);

}

-7-

top related