Repository 32bit  Forum
Repository 64bit  Wiki

Gestione Esami Universitari

Forum dedicato alla programmazione.

Moderatore: Staff

Regole del forum
1) Citare in modo preciso il linguaggio di programmazione usato.
2) Se possibile portare un esempio del risultato atteso.
3) Leggere attentamente le risposte ricevute.
4) Scrivere i messaggi con il colore di default, evitare altri colori.
5) Scrivere in Italiano o in Inglese, se possibile grammaticalmente corretto, evitate stili di scrittura poco chiari, quindi nessuna abbreviazione tipo telegramma o scrittura stile SMS o CHAT.
6) Appena registrati è consigliato presentarsi nel forum dedicato.

La non osservanza delle regole porta a provvedimenti di vari tipo da parte dello staff, in particolare la non osservanza della regola 5 porta alla cancellazione del post e alla segnalazione dell'utente. In caso di recidività l'utente rischia il ban temporaneo.

Gestione Esami Universitari

Messaggioda j0kers » mar mag 18, 2010 15:34

Salve ragazzi, sono qui a postare un piccolo programmino scritto da me in C, per la gestione tramite file, di esami universitari.
Una specie di libretto universitario per intenderci, con la possibilità di:

Aggiungere esami
Visualizzare esami
Calcolare la media dei voti, somma dei CFU e somma totale degli esami sostenuti

Questo è il codice sorgente:

Codice: Seleziona tutto
/* Semplice programma per calcolare la media degli
   esami sostenuti
*/

#include <stdio.h>
#include <string.h>
#include <ctype.h>

// Struttura dati Esami
struct esami {
   char nome[50];
   int voto;
   int cfu;
   char data[10];
};
struct esami libretto;

// Funzione Aggiungi Esame
// Aggiunge un esame a libretto
add_esame(){
   FILE *esami;
   int scelta, controllo;
   char libretto_file[20];
   char rsp[1];
   
   
   system("/bin/ls -1");
   printf("Scrivi il nome del libretto da aprire: ");
   scanf("%s",&libretto_file);
   if((esami=fopen(libretto_file,"r"))==NULL){
         printf("Il libretto non esiste!\n");
         sleep(1);
         return;
   }
   esami=fopen(libretto_file,"a");
   system("clear");
   // Inserimento Esame
   do{
      printf("Inserimento nuovo esame: \n\n");
      printf("Inserisci il nome dell'esame: ");
      scanf("%s",&libretto.nome);
      printf("Inserisci il voto (min 18 max 30): ");
      scanf("%d",&libretto.voto);
      printf("Inserisci i crediti (CFU): ");
      scanf("%d",&libretto.cfu);
      printf("Inserisci la data (gg/mm/aaaa): ");
      scanf("%s",&libretto.data);
      // Controllo dati inseriti
      if(libretto.voto<18 || libretto.voto>30){
         printf("Hai inserito un voto non valido!\n");
         sleep(1);
         return;
      }else if(libretto.cfu<3 || libretto.cfu >12){
         printf("Hai inserito CFU non validi!\n");
         sleep(1);
         return;
      }
      fprintf(esami,"Esame: %s - Voto: %d - CFU: %d - Data: %s\n",libretto.nome,libretto.voto,libretto.cfu,libretto.data);
      printf("Esame aggiunto con successo.\n");
      printf("Vuoi inserire un altro esame? (s/n): ");
      scanf("%s",&rsp);
      if(strlen(rsp)>1) return;
      controllo=strcmp(rsp,"n");
   }while(controllo!=0);

   fclose(esami);

   return;
}

// Funzione Crea Libretto
// Crea un nuovo libretto universitario
crea_libretto(){
   FILE *libretto;
   char nome_libretto[20];
   int confronto;
   
   system("clear");
   printf("ATTENZIONE: \tNel caso il libretto esiste già, esso verrà sovrascritto!\n");
   printf("Inserire \'esci\' per tornare al menu principale\n\n");
   printf("Inserisci il nome del libretto: ");
   scanf("%s",&nome_libretto);
   confronto=strcmp(nome_libretto,"esci");
   if(confronto==0) return;
   libretto=fopen(nome_libretto,"w");fclose(libretto);
   printf("Libretto creato con successo.\n ");
   sleep(1);
}

// Funzione Visualizza Libretto
// Visualizza gli esami del libretto
visualizza_libretto(){
   FILE *libretto;
   char nome_libretto[20];
   char buffer[300];
   
   system("clear;ls -1");
   printf("Inserisci il nome del libretto: ");
   scanf("%s",&nome_libretto);
   if((libretto=fopen(nome_libretto,"r"))==0){
      printf("Il libretto non esiste!\n");
      sleep(1);
      return;
   }else {
      while(!feof(libretto)){
         fgets(buffer,300,libretto);
         printf("%s \n",buffer);
      }
      fclose(libretto);
   }
   sleep(5);
}
// Funzione Calcola Media esami
// Calcola la media degli esami sostenuti
calcola_media(){
   FILE *libretto;
   FILE *media_file;
   char nome_libretto[20];
   char buffer[100];
   float media=0;
   int i=0,cfu=0;
   char cmd_media[50]="cat ", cmd_cfu[50]="cat ";
   
   system("clear;ls -1");
   printf("Inserisci il nome del libretto: ");
   scanf("%s",&nome_libretto);
   if((libretto=fopen(nome_libretto,"r"))==0){
      printf("Il libretto non esiste!\n");
      sleep(1);
      return;
   }else{
      // Crea il file media.txt per
      // per il calcolo della media
      strcat(cmd_media,nome_libretto);
      strcat(cmd_media," | sed 's/.*Voto: //' | awk '{print $1}' > media.txt");
      system(cmd_media);
      // Crea il file cfu.txt per
      // per il calcolo dei cfu
      strcat(cmd_cfu,nome_libretto);
      strcat(cmd_cfu," | sed 's/.*CFU: //' | awk '{print $1}' > cfu.txt");
      system(cmd_cfu);
      if((media_file=fopen("media.txt","r"))==NULL){
            printf("Errore apertura del file!\n");
            sleep(3);
            return;
      }
      while(!feof(media_file)){
         fgets(buffer,100,media_file);
         media=media+atoi(buffer);
         i++;
      }
      fclose(media_file);
      media=media / i;
      if((media_file=fopen("cfu.txt","r"))==NULL){
            printf("Errore apertura del file!\n");
            sleep(3);
            return;
      }
      i=0;
      while(!feof(media_file)){
         fgets(buffer,100,media_file);
         cfu=cfu+atoi(buffer);
         i++;
      }
      fclose(media_file);
      printf("Hai sostenuto %d esami con una media di %2.1f per un totale di %d CFU\n\n",i-1,media,cfu);
      system("rm -rf media.txt cfu.txt");
      char c=getchar();
      //sleep(10);
   }
}
// Funzione Principale MAIN

main(){
   int scelta;

   do{
      system("clear");
      printf("Gestione Libretto Esami Universitari\n\n");
      printf("Menu Principale: \n");
      printf("1) - Crea un libretto esami\n");
      printf("2) - Aggiungi un esame ad un libretto\n");
      printf("3) - Visualizza esami di libretto\n");
      printf("4) - Calcola la media degli esami sostenuti\n");
      printf("5) - Esci dal programma\n\n");
      printf("Scegli una opzione: ");
      scanf("%d",&scelta);
      // Controllo inserimento
      
      switch(scelta){
         case 1:
            crea_libretto();
            break;
         case 2:
            add_esame();
            break;
         case 3:
            visualizza_libretto();
            break;
         case 4:
            calcola_media();
            break;
      }
   }while(scelta!=5);
}


Devo ancora risolvere un paio di cose...Ad esempio nella funzione "main" il while viene ripetuto finquando non viene premuto il numero 5,
però se inserisco una lettera il programma va in errore.
L'altra cosa da risolvere è nelle funzioni visualizza,calcola ecc.. dopo aver mostrato i risultati ho dovuto inserire uno sleep al posto di getchar
perchè non si fermava la schermata ma rientrava subito alla main.

Accetto qualsiasi consiglio per perfezionare il codice. Grazie a tutti 8)
Ultima modifica di j0kers il mer mag 19, 2010 9:36, modificato 1 volta in totale.
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda Blallo » mar mag 18, 2010 15:57

al posto della scanf metti
Codice: Seleziona tutto
fgets(buf, TA, stdin);
sscanf(buf, "%d", &scelta);

ovviamente devi aggiungere l'header string.h
e devi definire anche una stringa (che chiamo buf in questo momento), TA è la dimensione della stringa
Io sono il detective Arsenio Magret, e porto sempre la camicia TATUATA!
Avatar utente
Blallo
Packager
Packager
 
Messaggi: 3212
Iscritto il: ven ott 12, 2007 10:37
Località: Torino / Torremaggiore (FG)
Nome Cognome: Savino Liguori
Slackware: 14.1 / 12.2
Kernel: 3.12.2-ck
Desktop: Openbox

Re: Gestione Esami Universitari

Messaggioda RedSkull92 » mar mag 18, 2010 16:16

è normale che il programma vada in errore se inserisci una lettera, perchè tu memorizzi i dati in un int, non in un char.
Stai attento che se vuoi leggere un libretto il cui nome ha spazi, non potrai farlo perchè scanf si ferma agli spazzi, potresti utilizzare fgets leggendo dal buffer stdin.
vediamo al funzione crea_libretto.
Codice: Seleziona tutto
if((esami=fopen(libretto_file,"r"))==NULL){
         printf("Il libretto non esiste!\n");
         sleep(1);
         return;
}
esami=fopen(libretto_file,"a");

non potevi fare direttamente
Codice: Seleziona tutto
if((esami=fopen(libretto_file,"a"))==NULL)
{
         printf("Il libretto non esiste!\n");
         sleep(1);
         return;
}
else
{
        ....
}

Codice: Seleziona tutto
printf("Inserisci il voto (min 18 max 30): ");
scanf("%d",&libretto.voto);

quì non fai un controllo per verificare se è davvero da 18 a 30, potresti utilizzare un'altro do while in modo da ripetere la richiesta in caso di valore errato, anzi di terminare la funzione senza alcun motivo,idem per i CFU
Codice: Seleziona tutto
printf("Inserisci la data (gg/mm/aaaa): ");
scanf("%s",&libretto.data);

quì potevi utilizzare sscanf in modo di poter verificare l'inserimento in modo corretto.
Codice: Seleziona tutto
printf("Vuoi inserire un altro esame? (s/n): ");
scanf("%s",&rsp);

perchè prendi una stringa ? devi inserire un s o una n quindi ti basta un char.
Potevi farla molto meglio ;)
nella funzione calcola_media ti sconsiglio di usare strcat ma di usare strncat la versione SICURA, perchè così sei a rischio di BoF
oppure usi scanf("%50s",nome_libretto); in modo da evitare nomi troppo lunghi.
Ora putroppo non ho più tempo, più tardi vedos e ci sono altre cose che potresti migliorare ;)
Saluti
Avatar utente
RedSkull92
Linux 2.6
Linux 2.6
 
Messaggi: 553
Iscritto il: mar apr 21, 2009 16:25
Località: Palermo
Slackware: 64bit -current
Kernel: 3.5.4
Desktop: FluxBox

Re: Gestione Esami Universitari

Messaggioda boh » mar mag 18, 2010 16:57

Per evitare l'errore all'inserimento della lettera apporta questa modifica allo switch:

Codice: Seleziona tutto
switch(scelta){
         case 1:
            crea_libretto();
            break;
         case 2:
            add_esame();
            break;
         case 3:
            visualizza_libretto();
            break;
         case 4:
            calcola_media();
            break;
         default:
            printf("Inserimento errato!");
      }
   }while(scelta!=5);


Il break all'ultima istruzione dello switch è opzionale :)
"Be yourself. Everyone else is already taken." ~ Oscar Wilde
Avatar utente
boh
Linux 2.6
Linux 2.6
 
Messaggi: 935
Iscritto il: gio set 15, 2005 23:00
Località: Milano
Slackware: 14.1 (x64)
Kernel: 3.10.17
Desktop: KDE 4.10.5

Re: Gestione Esami Universitari

Messaggioda targzeta » mar mag 18, 2010 17:39

Senza nulla togliere al lavoro, ma non era più semplice un file ben formato su cui avvii uno script che calcola la media? Quarda come ti risolvo i problemi:
j0kers ha scritto:Aggiungere esami

Codice: Seleziona tutto
nano file_esami.txt

j0kers ha scritto:Visualizzare esami

Codice: Seleziona tutto
cat file_esami.txt

j0kers ha scritto:Calcolare la media dei voti, somma dei CFU e somma totale degli esami sostenuti

Codice: Seleziona tutto
mio_script.sh file_esami.txt

Quello che devi fare è solo uno script awk o perl o altro,
Emanuele

P.S. Ripeto, non voglio essere polemico, è sempre bello vedere qualcuno che si cimenta in queste cose, solo che magari uno non ci pensa e le soluzioni migliori sono sempre dietro l'angolo.
Linux Registered User #454438
Se pensi di essere troppo piccolo per fare la differenza, prova a dormire con una zanzara -- Dalai Lama
20/04/2013 - Io volevo Rodotà
Avatar utente
targzeta
Iper Master
Iper Master
 
Messaggi: 6147
Iscritto il: gio nov 03, 2005 14:05
Località: Carpignano Sal. (LE) <-> Pisa
Nome Cognome: Emanuele Tomasi
Slackware: current
Kernel: latest stable
Desktop: IceWM

Re: Gestione Esami Universitari

Messaggioda j0kers » mar mag 18, 2010 17:54

Grazie per le risposte, rispondo a tutti.

Per spina:
Hai ragione però ho cercato quando meno possibile di utilizzare i comandi bash e di risolvere i problemi con il codice C.
Altrimenti lo creavo direttamente in bash shell e risolvevo molti problemi.

Per redskull:
La tua soluzione

if((esami=fopen(libretto_file,"a"))==NULL)
{
printf("Il libretto non esiste!\n");
sleep(1);
return;
}
else
{
....
}

non è molto esatta perchè apredo il file come append se inserisco un nome che non esiste il file viene comunque creato quindi la condizione di errore
non si verifica mai.
Per questo ho fatto una doppia apertura prima come "r" e poi come "a"
Con "r" se il file non esiste allora genera l'errore con "a" lo crea.
Inoltre per quanto riguarda i controlli su CFU e Voto se fai caso il controllo viene effettuato alla fine.

Per quanto riguarda il controllo nella main lo cambierò usando fgets.
Per gli sleep ??? Che mi consigliate??? In modo da bloccare le schermate 8)
comunque grazie a tutti per i consiglia
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda targzeta » mar mag 18, 2010 18:14

j0kers ha scritto:...
Per spina:
Hai ragione però ho cercato quando meno possibile di utilizzare i comandi bash e di risolvere i problemi con il codice C.
Altrimenti lo creavo direttamente in bash shell e risolvevo molti problemi.
...
Ok, allora buon lavoro :thumbright:

Emanuele
Linux Registered User #454438
Se pensi di essere troppo piccolo per fare la differenza, prova a dormire con una zanzara -- Dalai Lama
20/04/2013 - Io volevo Rodotà
Avatar utente
targzeta
Iper Master
Iper Master
 
Messaggi: 6147
Iscritto il: gio nov 03, 2005 14:05
Località: Carpignano Sal. (LE) <-> Pisa
Nome Cognome: Emanuele Tomasi
Slackware: current
Kernel: latest stable
Desktop: IceWM

Re: Gestione Esami Universitari

Messaggioda j0kers » mar mag 18, 2010 18:34


printf("Vuoi inserire un altro esame? (s/n): ");
scanf("%s",&rsp);

perchè prendi una stringa ? devi inserire un s o una n quindi ti basta un char.


Perchè se mettevo %c non si fermava sull'inserimento del carattere bensì andava avanti con il programma
Strano ma vero.
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda RedSkull92 » mar mag 18, 2010 18:39

Perchè se mettevo %c non si fermava sull'inserimento del carattere bensì andava avanti con il programma
Strano ma vero.

metti un fflush(stdin) dopo lo scanf e si sistema.
Inoltre per quanto riguarda i controlli su CFU e Voto se fai caso il controllo viene effettuato alla fine.

Si l'ho notato infatti ho scritto che è meglio effettuare un controllo con un do while in questo modo se si digita un numero errato viene riprosta la domanda di inserire il valore finchè non si inserire un numero corretto, nel modo fatto da te invece controlli alla fine ed esci dalla funzione se c'è errore, non ha senso,se io sbaglio dato dovrò riandare nel menu, fare la scelta e reinmettere i dati, molto molto scomodo, meglio fare il controllo prima così da evitare problemi.
Avatar utente
RedSkull92
Linux 2.6
Linux 2.6
 
Messaggi: 553
Iscritto il: mar apr 21, 2009 16:25
Località: Palermo
Slackware: 64bit -current
Kernel: 3.5.4
Desktop: FluxBox

Re: Gestione Esami Universitari

Messaggioda j0kers » mar mag 18, 2010 18:53

Ok allora sistemerò anche questo.
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda j0kers » mar mag 18, 2010 23:38

Per evitare l'errore all'inserimento della lettera apporta questa modifica allo switch:

Codice: Seleziona tutto
switch(scelta){
case 1:
crea_libretto();
break;
case 2:
add_esame();
break;
case 3:
visualizza_libretto();
break;
case 4:
calcola_media();
break;
default:
printf("Inserimento errato!");
}
}while(scelta!=5);


Non va bene.E' la stessa cosa il problema sta sulla scanf dell'intero.Credo che cambierò utilizzato sscanf o fgets.8)
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda Blallo » mar mag 18, 2010 23:50

più che altro vorrei capire perchè hai fatto in modo che ogni funzione apra e chiuda i file
fai una lista e poi magari fai una "chiudi file" per salvare tutto
aprire ogni volta è un po' pesante, e inoltre devi aggiungere il nome del file ogni volta
Io sono il detective Arsenio Magret, e porto sempre la camicia TATUATA!
Avatar utente
Blallo
Packager
Packager
 
Messaggi: 3212
Iscritto il: ven ott 12, 2007 10:37
Località: Torino / Torremaggiore (FG)
Nome Cognome: Savino Liguori
Slackware: 14.1 / 12.2
Kernel: 3.12.2-ck
Desktop: Openbox

Re: Gestione Esami Universitari

Messaggioda j0kers » mer mag 19, 2010 9:35

Infatti ho cambiato il menu in questo modo:
Codice: Seleziona tutto
   
printf("\nGestione Libretto Esami Universitari\n\n");
printf("Menu Principale: \n");
printf("1) - Crea un libretto esami\n");
printf("2) - Apri libretto\n");
printf("3) - Aggiungi un esame ad un libretto\n");
printf("4) - Visualizza esami di libretto\n");
printf("5) - Calcola la media degli esami sostenuti\n");
printf("6) - Esci dal programma\n\n");
printf("Scegli una opzione: ");

Dove prima di qualsiasi operazione bisogna aprire il libretto (file testo) altrimenti genera un errore
di file non trovato.

Per quanto riguarda il controllo nella scanf della main ho risolto in questo modo.

Codice: Seleziona tutto
if(scanf("%d",&scelta)==0){
   printf("Valore non valido!\n");
   break;
}

Per quanto riguarda l'inserimento di un nuovo esame se uso la fgets e sscanf non si ferma sull'immissione dati
Codice: Seleziona tutto
fgets(buffer,MAX,stdin);
sscanf(buffer,"%s",&libretto.nome);


MAX=100 e buffer[MAX]
Perchè non mi fa leggere da stdin ?
Avatar utente
j0kers
Linux 2.4
Linux 2.4
 
Messaggi: 418
Iscritto il: dom lug 22, 2007 0:31
Slackware: 13
Kernel: 2.6.32
Desktop: xfce4

Re: Gestione Esami Universitari

Messaggioda birg81 » mer mag 19, 2010 12:47

Mi rendo conto che attrarrò le critiche di molti ma benché un vero programmatore scrive in C se non in linguaggio macchina, forse era il caso di scriverlo in Java il ché è importantissimo per l'utente medio
birg81
Linux 2.6
Linux 2.6
 
Messaggi: 760
Iscritto il: lun gen 16, 2006 10:57
Località: Castellammare di Stabia (NA)
Nome Cognome: Biagio
Slackware: 12.2
Kernel: 3.4.7
Desktop: LxDE
Distribuzione: ArchLinux

Re: Gestione Esami Universitari

Messaggioda Blallo » mer mag 19, 2010 13:21

birg81 ha scritto:Mi rendo conto che attrarrò le critiche di molti ma benché un vero programmatore scrive in C se non in linguaggio macchina, forse era il caso di scriverlo in Java il ché è importantissimo per l'utente medio

e che c'entra scusa? :shock:
Io sono il detective Arsenio Magret, e porto sempre la camicia TATUATA!
Avatar utente
Blallo
Packager
Packager
 
Messaggi: 3212
Iscritto il: ven ott 12, 2007 10:37
Località: Torino / Torremaggiore (FG)
Nome Cognome: Savino Liguori
Slackware: 14.1 / 12.2
Kernel: 3.12.2-ck
Desktop: Openbox

Prossimo

Torna a Programmazione

Chi c’è in linea

Visitano il forum: Nessuno e 1 ospite