Domanda liste concatenate

sara20

Utente Silver
6 Febbraio 2020
116
29
1
54
Ultima modifica:
salve..devo fare un progetto con liste che permetti di stampare, richiedere e restituire un libro pero ho a-priori 15 libri(ho utilizzato un file)vi posto il mio codice la stampa funziona mentre la richiesta e la restituzione no potete aiutarmi vi prego....
Codice:
#include <stdio.h>


#include <stdlib.h>


#define len 35


typedef struct {


    char nome[20];


   char cognome[20];


    char matricola[20]


  struct Studente *next;


}Studente;





typedef struct {


    Studente element[len];


    int num_studente;


}List;





struct lista


{


char titolo[10];


char autore[10]


int cod_id;


struct lista *next;


};





typedef struct {


    struct lista elementi[len];


   int num_libri;


}Libro;





int Cerca_Titolo(Libro list ,char titolo[10]){


    int j;


   int presenza=-1;


    for(j=0; j<list.num_libri; j++) {


        if(strcmp(list.elementi[j].titolo, titolo)==0){


            presenza=1;


        }


    }


    return presenza;


}





struct lista *creaNodo(FILE *fp)


{


    struct lista *temp=(struct lista *)malloc(sizeof(struct lista ));





    fscanf(fp, "%s %s %d", temp->titolo[20], temp->autore[10],&temp->cod_id);


    temp->next=NULL;





return (temp);


}





void stampaLista(struct lista *top)


{


    if (top==NULL)


    {


        printf("\n--------------\n\n");


    }


    else





    if (top!=NULL && top->titolo!=0)


    {


        printf("%s %s %d", top->titolo[10],  top->autore[20], &top->cod_id);


                stampaLista(top->next);


    


    }


}





FILE *apriFile(FILE *fp)


{


    fp=fopen("Libri.txt", "r");


    if (fp==NULL)


    {


    perror("");


    exit(1);


    }





return (fp);


}





struct lista *CREA(struct lista *TOP){


struct lista *tmp=(struct lista*)malloc(sizeof(struct lista));


tmp->next=TOP;


strcpy(tmp->titolo,TOP->titolo[10]);


strcpy(tmp->autore,TOP->autore[10]);


tmp->cod_id = TOP->cod_id;


return tmp;


}





int menu(){


    int scelta; /*Questa variabile sarà utilizzata nella switch per decidere che cosa fare...*/


    //char nome;//utilizzata per inserire il nome dell'utente


    //char matricola;//utilizzata per inserire la matricola dello studente


printf("\n* * * * * * * * * * * * * * * * * * * * * * *\nBenvenuto nel programma di gestione biblioteca\n* * * * * * * * * * * * * * * * * * * * * * *\n");


    //printf("Inserisci il nome:");


    //scanf("%s", &nome);


   // printf("Inserisci il matricola:");


    //scanf("%s", &matricola);


    printf(" 1. Mostra archivio\n");


    printf(" 2. Richiedi libro\n");


    printf(" 3. Restituire libro\n");


    printf(" 4. Esegui richiesta\n");


    printf(" 5. Uscire\n");


    printf("Inserisci scelta:");


       scanf("%d",&scelta); /*Viene inserito nella variabile var il numero inserito dall'utente e di conseguenza inserito nel ciclo Switch*/


    while(scelta<0 || scelta>5) {


        printf("Questo tasto non consente di effetuare scelte! Riprova!\n");


        printf("Scelta: ");


        scanf("%d", &scelta);


        return scelta;


    }


    return scelta;


}





List Inserimento_Studente(){


   List lista;


   int i;


   printf("\nQuanti libri vuoi restituire?:");


    scanf("%d",&lista.num_studente);


   fflush(stdin);


   for(i=0; i <lista.num_studente; i++) {


        printf("\nInserisci nome: ");


       gets(&lista.element[i].nome[20]);


        printf("\nInserisci cognome[20]: ");


       gets(&lista.element[i].cognome[20]);


       printf("\nInserisci matricola: ");


        scanf("%s", &lista.element[i].matricola);


        fflush(stdin);


}


    return lista;


}





int main() {





char buf[200];


char *res;


FILE *fp=NULL;


int scelta;


struct lista *top=NULL;


char titolo[len];


int presenza;


Libro L;


List l;








while((scelta = menu())){





    switch (scelta) /* Creo uno switch con 5 case, uno per ogni possibile scelta */


{


case 1: /*stampa lista*/


         /* apre il file */


        fp=apriFile(fp);





            while (!feof(fp))


            {


            res=fgets(buf, 200, fp);


            if( res==NULL )


              break;


            printf("%s", buf);


            }


        fclose(fp); /* chiudo il puntatore a file gestito in READ */





        stampaLista(top);


    


        break;





case 2: /* Se l'utente preme il tasto 2 si cerca se c'e il libro e richiedere un libro tramite il codice*/





        printf("\nInserisci titolo libro da richiedere:");








        fflush(stdin);








        gets(titolo);








        fp=apriFile(fp);








           while(!feof(fp)) {








        presenza = Cerca_Titolo(L,titolo);








                if(titolo != -1) {








                    printf("Il libro cercato non e' presente nell'archivio ed il libro non e' disponibile\n");








                    l = Inserimento_Studente();








                } else {








                  printf("Il libro cercato non e' presente nell'archivio ed il libro non e' disponibile\n");








            }





           }





            fclose(fp);








           break;


case 3: /* Case costruito per restituire un libro tramite codice*/


   


        break;


    


case 4: /*esegui richiesta*/


        break ;


case 5: /*Se l'utente vuole uscire dalla biblioteca*/


printf("Grazie per aver scelto il servizio di gestione della biblioteca, torna a trovarci!\n");


        break;





default: /*Se l'utente sbaglia ad inserire il numero*/


        printf("Questo tasto non consente di effetuare scelte! Riprova!\n");


        break;





      } /*Fine switch*/


   } /*Fine do*/


    return scelta;


} /*Fine main*/
 
Ultima modifica:
Ciao.
Fai in piu' punti lo stesso errore, ossia dichiari una variabile atta a contenere UN singolo carattere, invece di un array di caratteri.
(solo titolo e' dichiarato correttamente)

C:
char nome; // "contenitore" di un singolo carattere: puo' contenere solo una lettera!
char nome[20]; // "contenitore" per 20 caratteri: ora puo' contenere un nome... fino a 20 lettere

Ovviamente, di conseguenza, quando dovrai "passare" questo "contenitore" attraverso le funzioni che hai dichiarato, dovrai farlo con la sintassi appropriata (per indirizzo, non per valore)
 
Ultima modifica:
si ho modificato...ma comunque non mi funziona...se potete mi aiutate tra un po’ di giorni devo consegnarlo so che non si può però se si può fare “uno strappo alla regola”
 
Ultima modifica:
Il mio consiglio non era inteso a dire: prendi [20] e aggiungilo dappertutto.
1) Anzitutto devi valutare quanto grandi debbano essere questi contenitori: 20 e' OK per un nome, ma non per un titolo...
2) Il mio codice era relativo alla dichiarazione! per cio' che riguarda il passaggio dei parametri: per ogni singola funzione devi considerare cosa stai "passando", e come passarlo: aggiungere [20] a tutto cio' che hai dichiarato, non e' la maniera corretta.
Riguarda il passaggio dei parametri delle funzioni, per valore e per indirizzo, e valuta qual'e' il modo corretto... per esempio:
C:
strcpy(tmp->titolo,TOP->titolo[20]); // qui stai utilizzando DUE modi DIVERSI per passare i parametri, per una variabile dello stesso tipo!!!
// il primo parametro 'e passato correttamente, il secondo no!

Ripeto, rileggi il passaggio dei parametri delle funzioni, non andare per tentativi.
(ed ovviamente anche la differenza dall'accedere ad un indirizzo e/o al valore, argomento: i puntatori)
 
Il mio consiglio non era inteso a dire: prendi [20] e aggiungilo dappertutto.
1) Anzitutto devi valutare quanto grandi debbano essere questi contenitori: 20 e' OK per un nome, ma non per un titolo...
2) Il mio codice era relativo alla dichiarazione! per cio' che riguarda il passaggio dei parametri: per ogni singola funzione devi considerare cosa stai "passando", e come passarlo: aggiungere [20] a tutto cio' che hai dichiarato, non e' la maniera corretta.
Riguarda il passaggio dei parametri delle funzioni, per valore e per indirizzo, e valuta qual'e' il modo corretto... per esempio:
C:
strcpy(tmp->titolo,TOP->titolo[20]); // qui stai utilizzando DUE modi DIVERSI per passare i parametri, per una variabile dello stesso tipo!!!
// il primo parametro 'e passato correttamente, il secondo no!

Ripeto, rileggi il passaggio dei parametri delle funzioni, non andare per tentativi.
Okok ho cercato di modificare...diciamo che prima volevo creare la struttura che funzionava con le funzioni e poi vado a modificare nomi e dimensioni
 
Ultima modifica:
Quando ti "consiglio" di riguardarti l'argomento dei puntatori e del passaggio dei parametri (per valore ed indirizzo), non e' per volerti far studiare per forza, e' solo perche' si percepisce in modo palese la tua confusione su quegli argomenti..

Con strcpy, nel messaggio precedente, ho fatto un esempio per indirizzarti sull'argomento, ma il tuo programma e' pieno di questo tipo di "fraintendimenti", a partire delle funzioni printf, scanf, gets , o anche quando "dovresti" valutare un puntatore.

Cerco di essere un po' piu' esplicito, anche se brevemente (meglio se approfondisci l'argomento) :
C:
// La funzione strcpy e' definita:
char * strcpy ( char * destination, const char * source ); // accetta in ingresso due "indirizzi"

strcpy(tmp->titolo, // qui stai passando correttamente l'indirizzo
TOP->titolo[20]); // qui staipassando il VALORE del 21esimo carattere: devi passare un indirizzo, NON un valore

Ci sono diversi errori simili a questo, e il programma non verrebbe nemmeno compilato.
Sarebbe buona norma seguire cio' che ci dice il compilatore (che ci "avvisa" per ogni errore o ci da un avvertimento "warning" quando qualcosa non quadra alla perfezione), andare a vedere sulla riga segnalata di cosa si tratta e cercare di correggerlo.
Seguendo cio' che ti dice il compilatore potresti quanto meno mettere a posto le funzioni che ti ho citato precedentemente, e qualche altra cosa che ti segnala..

Ovviamente per ogni errore che il compilatore ti segnala e non riesci a comprendere, riportalo qui e vedro' di aiutarti
 
Ultima modifica:
ho modificato qualcosa e forse ci sono altri errori ma al di la di questo vorrei capire come mai la la richiesta del libro non mi funziona
Codice:
#include <stdio.h>


#include <stdlib.h>


#include <string.h>


#define MAXLEN 100





struct libri{


    char titolo[100];


    char autore[100];


    int cod_id;


    struct libri *next;


};





typedef struct {


    struct libri elementi[100];


   int num_libri;


}Libro;





int Cerca_Titolo(Libro list ,char titolo);


struct libri initList(char titolo,char autore,int cod_id);


struct libri insertHead(struct libri L, char titolo,char autore, int cod_id);


//struct libri *CREA_LISTA(struct libri *TOP);


int menu();


struct libri *leggiFile(FILE *fp, struct libri *lista);


void scriviLista(struct libri *lista);


void scriviFile(FILE *fp, struct libri *lista);


static struct libri *inserisciLista(struct libri *nodo, struct libri *lista);


static struct libri *nuovoNodo(char *titolo,char *autore, int cod_id);


static void freeNodo(struct libri *nodo);


void gestioneErrore();


void freeLista(struct libri *lista);


void stampaLista(struct libri *top);





int main() {


    int scelta;


    FILE *fp;


    struct libri *lista=NULL;


    struct lista *top = NULL;


    int cod_id;


    char titolo;


    char autore;


    struct libri L;


    int presenza;


    Libro l;


    


    


//lista = nuovoNodo(titolo,autore,cod_id);


//CREA_LISTA(lista);


//lista = inserisciLista(L,autore);





while((scelta = menu())){


switch (scelta) /* Creo uno switch con 5 case, uno per ogni possibile scelta */





{


 case 1: /*stampa lista*/





       fp = fopen("Libri.txt","r");


        lista = leggiFile(fp, lista);


        fclose(fp);


        scriviLista(lista);


        //stampaLista(top);


    break;





    case 2: /* Se l'utente preme il tasto 2 si cerca se c'e il libro e richiedere un libro tramite il codice*/





    printf("\nInserisci titolo libro da richiedere:");


        scanf("%s", &titolo);


        //fflush(stdin);





       // gets(titolo);





         fp = fopen("Libri.txt","r");


       lista = leggiFile(fp, lista);


        //fclose(fp);


       // scriviLista(lista);








    presenza = Cerca_Titolo(l,titolo);


        if(titolo != -1) {


printf("Il libro cercato  e' presente nell'archivio ed il libro  e' disponibile\n");





      //  l = Inserimento_Studente();





            } else {





printf("Il libro cercato non e' presente nell'archivio ed il libro non e' disponibile\n");





     }








            fclose(fp);


    break;





case 3: /* Case costruito per restituire un libro tramite codice*/








       








        break;








        








case 4: /*esegui richiesta*/








        break ;








case 5: /*Se l'utente vuole uscire dalla biblioteca*/








printf("Grazie per aver scelto il servizio di gestione della biblioteca, torna a trovarci!\n");








        break;

















default: /*Se l'utente sbaglia ad inserire il numero*/








        printf("Questo tasto non consente di effetuare scelte! Riprova!\n");








        break;

















      } /*Fine switch*/








   } /*Fine do*/








    return scelta;








} /*Fine main*/





int menu(){


int scelta; /*Questa variabile sarà utilizzata nella switch per decidere che cosa fare...*/


    printf("* * * * * * * * * * * * * * * * * * *  \nBenvenuto nel programma di gestione biblioteca\n* * * * * * * * * * * * * * * * * * *  \n");


    





    printf(" 1. Mostra archivio\n");


    printf(" 2. Richiedi libro\n");


    printf(" 3. Restituire libro\n");


    printf(" 4. Esegui richiesta\n");


    printf(" 5. Uscire\n");


    printf("Inserisci scelta:");


    scanf("%d",&scelta); /*Viene inserito nella variabile var il numero inserito dall'utente e di conseguenza inserito nel ciclo Switch*/


    while(scelta<0 || scelta>5) {     printf("Questo tasto non consente di effetuare scelte! Riprova!\n");


        printf("Scelta: ");


        scanf("%d", &scelta);


      return scelta;


 }


  return scelta;


}


static struct libri *nuovoNodo(char *titolo,char *autore, int cod_id)


{


  struct libri *nodo;





  nodo = (struct libri *) malloc(sizeof(struct libri));


  if (nodo == NULL) return NULL;


  strcpy(nodo->titolo,titolo);


  strcpy(nodo->autore, autore);


  nodo->cod_id =cod_id;


  nodo->next = NULL;


    


  return nodo;


}





static void freeNodo(struct libri *nodo)


{


  free((void *) nodo);


}





static struct libri *inserisciLista(struct libri *nodo, struct libri *lista)


{


  if (lista==NULL) return nodo;


  lista->next = inserisciLista(nodo, lista->next);


  return lista;


}








void gestioneErrore()


{


  printf("Errore\n");





  exit(0);


}





void freeLista(struct libri *lista)


{


  if (lista != NULL) {


    freeLista(lista->next);


    freeNodo(lista);


  }


}








void scriviLista(struct libri *lista)


{


  while (lista!=NULL) {


    printf("%s %s %d\n",lista->titolo,lista->autore,lista->cod_id);


    lista = lista->next;


  }


  printf("\n");


}





struct libri *leggiFile(FILE *fp, struct libri *lista)


{


  char titolo[256], autore[256];


  int cod_id;


  struct libri *nodo;





  while(fscanf(fp,"%s%s%d",titolo,autore,&cod_id)==3){


    nodo = nuovoNodo(titolo,autore,cod_id);


    if (nodo == NULL)


        gestioneErrore();


    lista = inserisciLista(nodo, lista);


  }


  return lista;


}





void scriviFile(FILE *fp, struct libri *lista)


{


  while (lista!=NULL) {


    fprintf(fp,"%s %s %d \n",lista->titolo,lista->autore,lista->cod_id);


    lista = lista->next;


  }


}





void stampaLista(struct libri *top)


{


    if (top == NULL) {


        printf("\n--------------\n\n");


    }else


       if (top!=NULL && top->titolo!=0) {


printf("%s %s %d", top->titolo,  top->autore, &top->cod_id);


    stampaLista(top->next);





    }





}


//struct libri *CREA_LISTA(struct libri *TOP){


//struct libri *tmp=(struct libri*)malloc(sizeof(struct libri));


//tmp->next=TOP;


//strcpy(tmp->titolo,TOP->titolo);


//strcpy(tmp->autore,TOP->autore);


//tmp->cod_id=TOP->cod_id;


//return tmp;


//}





int Cerca_Titolo(Libro list ,char titolo){


int j;


int presenza=-1;


  for(j=0; j<list.num_libri; j++) {


      if(strcmp(list.elementi[j].titolo, &titolo)==0){


          presenza=1;


   }


}





 return presenza;





}
Messaggio unito automaticamente:

Quando ti "consiglio" di riguardarti l'argomento dei puntatori e del passaggio dei parametri (per valore ed indirizzo), non e' per volerti far studiare per forza, e' solo perche' si percepisce in modo palese la tua confusione su quegli argomenti..

Con strcpy, nel messaggio precedente, ho fatto un esempio per indirizzarti sull'argomento, ma il tuo programma e' pieno di questo tipo di "fraintendimenti", a partire delle funzioni printf, scanf, gets , o anche quando "dovresti" valutare un puntatore.

Cerco di essere un po' piu' esplicito, anche se brevemente (meglio se approfondisci l'argomento) :
C:
// La funzione strcpy e' definita:
char * strcpy ( char * destination, const char * source ); // accetta in ingresso due "indirizzi"

strcpy(tmp->titolo, // qui stai passando correttamente l'indirizzo
TOP->titolo[20]); // qui staipassando il VALORE del 21esimo carattere: devi passare un indirizzo, NON un valore

Ci sono diversi errori simili a questo, e il programma non verrebbe nemmeno compilato.
Sarebbe buona norma seguire cio' che ci dice il compilatore (che ci "avvisa" per ogni errore o ci da un avvertimento "warning" quando qualcosa non quadra alla perfezione), andare a vedere sulla riga segnalata di cosa si tratta e cercare di correggerlo.
Seguendo cio' che ti dice il compilatore potresti quanto meno mettere a posto le funzioni che ti ho citato precedentemente, e qualche altra cosa che ti segnala..

Ovviamente per ogni errore che il compilatore ti segnala e non riesci a comprendere, riportalo qui e vedro' di aiutarti
ciao,ho modificato un pò di cose ma la ricerca del libro tramite il titolo non mi funziona...puoi aiutarmi?

#include <stdio.h>


#include <stdlib.h>


#include <string.h>


#define MAXLEN 100





struct libri{


char titolo[30];


char autore[30];


int cod_id;


struct libri *next;


};


typedef struct libri* List;


typedef struct {


struct libri elementi[100];


int num_libri;


}Libro;





void ricerca (struct libri *l);


int menu(void);


struct libri *leggiFile(FILE *fp, struct libri *lista);


void scriviLista(struct libri *lista);


void scriviFile(FILE *fp, struct libri *lista);


struct libri *nuovoNodo(char *titolo,char *autore, int cod_id);


void gestioneErrore(void);


void stampaLista(struct libri *top);


struct libri *inserisciLista(struct libri *nodo, struct libri *lista);





int main() {


int scelta;


FILE *fp;


struct libri *lista=NULL;


char titolo;











fp = fopen("Libri.txt","r");


if (fp == NULL) gestioneErrore();


lista = leggiFile(fp, lista);


fclose(fp);


while((scelta = menu())){


switch (scelta) /* Creo uno switch con 5 case, uno per ogni possibile scelta */


{


case 1: /*stampa lista*/


scriviLista(lista);


break;


case 2: /* Se l'utente preme il tasto 2 si cerca se c'e il libro e richiedere un libro tramite il codice*/





printf("Inserisci il titolo del libro da cercare: ");


scanf("%s", &titolo);


ricerca(lista);


break;





case 3: /* Case costruito per restituire un libro tramite codice*/


break;





case 4: /*esegui richiesta*/


break ;





case 5: /*Se l'utente vuole uscire dalla biblioteca*/


printf("Grazie per aver scelto il servizio di gestione della biblioteca, torna a trovarci!\n");


break;





default: /*Se l'utente sbaglia ad inserire il numero*/


printf("Questo tasto non consente di effetuare scelte! Riprova!\n");





break;





} /*Fine switch*/





} /*Fine do*/





return scelta;





} /*Fine main*/





int menu(){


int scelta; /*Questa variabile sarà utilizzata nella switch per decidere che cosa fare...*/


printf("* * * * * * * * * * * * * * * * * * * \nBenvenuto nel programma di gestione biblioteca\n* * * * * * * * * * * * * * * * * * * \n");





printf(" 1. Mostra archivio\n");


printf(" 2. Richiedi libro\n");


printf(" 3. Restituire libro\n");


printf(" 4. Esegui richiesta\n");


printf(" 5. Uscire\n");


printf("Inserisci scelta:");


scanf("%d",&scelta); /*Viene inserito nella variabile var il numero inserito dall'utente e di conseguenza inserito nel ciclo Switch*/


while(scelta<0 || scelta>5) { printf("Questo tasto non consente di effetuare scelte! Riprova!\n");


printf("Scelta: ");


scanf("%d", &scelta);


return scelta;





}


return scelta;


}





struct libri *nuovoNodo(char *titolo,char *autore, int cod_id)





{





struct libri *nodo;


nodo = (struct libri *) malloc(sizeof(struct libri));


if (nodo == NULL) return NULL;


strcpy(nodo->titolo,titolo);


strcpy(nodo->autore, autore);


nodo->cod_id =cod_id;


nodo->next = NULL;


return nodo;


}





void gestioneErrore()


{


printf("Errore\n");


exit(0);


}





struct libri *leggiFile(FILE *fp, struct libri *lista)


{





char titolo[30], autore[30];


int cod_id;


struct libri *nodo;


while(fscanf(fp,"%s%s%d",titolo,autore,&cod_id)==3){


nodo = nuovoNodo(titolo,autore,cod_id);


if (nodo == NULL)


gestioneErrore();


lista = inserisciLista(nodo, lista);


}


return lista;


}





void scriviFile(FILE *fp, struct libri *lista) {


while (lista!=NULL) {


fprintf(fp,"%s %s %d \n",lista->titolo,lista->autore,lista->cod_id);


lista = lista->next;


}


}





void stampaLista(struct libri *top)


{


if (top == NULL) {


printf("\n--------------\n\n");


}else


if (top!=NULL && top->titolo!=0) {


printf("%s %s %d", top->titolo, top->autore, &top->cod_id);


stampaLista(top->next);


}


}








void scriviLista(struct libri *lista) {


while (lista!=NULL) {


printf("%s %s %d\n",lista->titolo,lista->autore,lista->cod_id);


lista = lista->next;


{


printf("\n");


}


}


}





void ricerca (struct libri *l){


int trovato = 0 ;


char titolo;


char nome;


char matricola;


while (l != NULL && trovato != 1) {


if(strcmp(l->titolo, &titolo)==0) {


printf("\nIl libro cercato e' presente nell'archivio ed il libro e' disponibile");


trovato=1;


printf("\nInserisci nome:");


scanf("%s", &nome);


printf("\nInserisci matricola:");


scanf("%s", &matricola);


}


l = l->next;


}





if(trovato != 1)


printf("\n Libro non trovato");





}





struct libri *inserisciLista(struct libri *nodo, struct libri *lista)


{


if (lista==NULL) return nodo;


lista->next = inserisciLista(nodo, lista->next);


return lista;


}