001: #include<stdio.h>
002: #include<stdlib.h>
003: #include<string.h>
004: 
005: 
006: 
007: struct comune
008: {
009:   char nome[41], provincia[3], regione[4], cap[6]; // aumentati di +1 per carattere nullo terminazione stringhe
010:   unsigned int popolazione;
011: };
012: 
013: int confrontapopolazione(const void *a, const void *b)
014: {
015:   const struct comune *pa=a;
016:   const struct comune *pb=b;
017:   return pa->popolazione -  pb->popolazione;
018: }
019: 
020: 
021: int confrontanome(const void *a, const void *b)
022: {
023:   const struct comune *pa=a;
024:   const struct comune *pb=b;
025:   return strcmp(pa->nome, pb->nome);
026: }
027: 
028: 
029: int main(int argc, char **argv){
030:   FILE *fp=fopen("comuni.csv", "r");
031: 
032:   if(!fp)
033:   {
034:     perror("Errore apertura file");
035:     exit(EXIT_FAILURE);
036:   }
037: 
038:   //PUNTO 1
039:   char riga[71];
040:   int nrighe=0;
041:   while(fscanf(fp," %[^\n]",riga) == 1 ) nrighe++; // lo spazio iniziale mi toglie eventuali spaziature tra cui lo \n dal buffer
042:   printf("Il file contiene %d righe\n", nrighe);
043: 
044:   // PUNTO 2
045: 
046:   // alloco array dinamicamente
047:   struct comune *dati=malloc(nrighe*sizeof(struct comune));
048:   if(!dati)
049:   {
050:     fprintf(stderr, "Errore in allocazione di %ld byte\n", nrighe*sizeof(struct comune));
051:     exit(EXIT_FAILURE);
052:   }
053: 
054:   //  rileggo file
055:   fseek(fp, 0, SEEK_SET);
056:   int i=0; // contatore posizione array
057:   while(fscanf(fp," %[^;];%[^;];%[^;];%[^;];%u",
058:   dati[i].nome,
059:   dati[i].provincia,
060:   dati[i].regione,
061:   dati[i].cap,
062:   &dati[i].popolazione
063:   ) == 5 )
064:   {
065:     ++i;
066:   }
067:   fclose(fp);
068: 
069:   // punto 3
070:   while(1)
071:   {
072:     int scelta;
073:     printf("Inserisci:\n\t0 esci\n\t1 ricerca per CAP\n\t2 report regione\n\t3 report provincia\n\t4 ordinamento per popolazione\n\t5 ordinamento per nome comune\n\t6 salvataggio file\nScelta: ");
074: 
075:     scanf("%d", &scelta);
076:     switch(scelta)
077:     {
078:       case 0:
079:   exit(EXIT_SUCCESS);
080:       case 1:
081:   {  // se definisco variabili locali devo racchiudere il tutto in un blocco di codice negli switch-case
082:     char cap[6];
083:     printf("Inserire CAP: ");
084:     scanf("%s", cap); // XXX da non farsi nel mondo reale, meglio fgets(cap,6,stdin);
085:     for(i=0; i<nrighe && strcmp(cap,dati[i].cap); ++i); // esco se trovo o a fine righe
086:     if(i<nrighe)
087:       printf("Nome:\t%s\nProvincia:\t%s\nRegione:\t%s\nCAP:\t%s\nPopolazione:\t%u\n",
088:     dati[i].nome,
089:     dati[i].provincia,
090:     dati[i].regione,
091:     dati[i].cap,
092:     dati[i].popolazione
093:     );
094:     else
095:       printf("CAP non trovato\n\n");
096:   }
097:   break;
098:       case 2:
099:   {
100:     char regione[4];
101:     printf("Inserire sigla regione: ");
102:     scanf("%s", regione); // XXX come sopra
103:     unsigned int totpopolazione=0;
104:     printf("I Comuni della regione %s sono:\n", regione);
105:     for(i=0; i<nrighe; ++i) // devo scandire tutte le righe
106:     {
107:       if(!strcmp(dati[i].regione, regione))
108:       {
109:         printf(" Nome:\t%s\n Popolazione:\t%u\n\n",dati[i].nome,dati[i].popolazione);
110:         totpopolazione += dati[i].popolazione;
111:       }
112:     }
113:     printf(" Popolazione totale; %u\n", totpopolazione);
114:   }
115:   break;
116:       case 3:
117:   {
118:     char provincia[3];
119:     printf("Inserire sigla provincia: ");
120:     scanf("%s", provincia); // XXX come sopra
121:     unsigned int totpopolazione=0;
122:     printf("I Comuni della provincia %s sono:\n", provincia);
123:     for(i=0; i<nrighe; ++i) // devo scandire tutte le righe
124:     {
125:       if(!strcmp(dati[i].provincia, provincia))
126:       {
127:         printf(" Nome:\t%s\n Popolazione:\t%u\n\n",dati[i].nome,dati[i].popolazione);
128:         totpopolazione += dati[i].popolazione;
129:       }
130:     }
131:     printf(" Popolazione totale; %u\n", totpopolazione);
132:   }
133:   break;
134: 
135:       case 4:
136:   qsort(dati, nrighe, sizeof(struct comune), confrontapopolazione);
137:   break;
138:       case 5:
139:   qsort(dati, nrighe, sizeof(struct comune), confrontanome);
140:   break;
141:       case 6:
142:   fp = fopen("out.dat", "wb"); // scrivo su file binario per semplicita' anche se in questo caso non e' la scelta migliore
143:   if(!fp)
144:   {
145:     perror("Errore apertura file in scrittura");
146:     exit(EXIT_FAILURE);
147:   }
148: 
149:   fwrite(dati, sizeof(struct comune), nrighe, fp);
150:   printf("%lu byte scritti in ""out.dat""\n", sizeof(struct comune)*nrighe);
151:   fclose(fp);
152:   break;
153:       default:
154:   fprintf(stderr, "Errore: scelta non valida\n");
155:   break;
156:     }
157:   }
158: 
159: 
160: 
161: 
162: 
163:   return 0;
164: }
165: 
166: