Puntatore ed errore di segmentazione

di il
2 risposte

Puntatore ed errore di segmentazione

Salve ragazzi,
sto facendo gli esercizi del capitolo 7 del libro di Aguilar (che usiamo all'universita).
L'esercizio mi chiede di creare un db con un array di struttura. Sto lavorando su Ubuntu e compilo da terminale con gcc (metodo usato all'uni)..

Qui il codice (volevo metterne solo una parte, ma se posso volevo chiedere altre cose):
#include <stdio.h>
#include <stdlib.h>

enum {MOROSO, RITARDO, PAGATO};

struct anagrafica{
                char nome[20];
                int ordini;
                float prezzo_unit;
                int stato;
};

const int MAX=10;  //dovrebbe essere 100 

void inserisci(struct anagrafica a[], int* i){
     int val,temp;
     float ftemp;
     printf("Cliente n°%d\n", *i+1);
     printf("Inserire nome cliente: \n");
     scanf("%20s", a[*i].nome);
     printf("Inserire pezzi ordinati:\n");
     scanf("%d", &temp);      //ho dovuto fare sto giro per evitare unn warning 
     a[*i].ordini=temp;           // (o forse un errore nel compilatore)
     printf("Inserire prezzo unitario:\n");
     scanf("%f", &ftemp);
     a[*i].prezzo_unit=ftemp;
     printf("Inserire stato:\n1-Moroso\n2-InRitardo\n3-Pagato");
     scanf("%d", &val);
     switch (val){
         case 1: a[*i].stato = MOROSO;
         case 2: a[*i].stato = RITARDO;
         case 3: a[*i].stato = PAGATO;
     }
     
}

void stampa(struct anagrafica a[], int* i){
     int val,n;
     for (n=0; n<*i; n++){
             printf("%d - %20s\t%d\t%f\t", *i,a[*i].nome,a[*i].ordini,a[*i].prezzo_unit);
             val=a[*i].stato;
             switch(val){
                case 0: printf("MOROSO"); break;
                case 1: printf("IN RITARDO"); break;
                case 2: printf("PAGATO"); break;
             }
      }
}

int menu(){
        int i,n;
        for (n=0;n<30;n++) printf("\n");
        printf("++++++++++++++++++++++++++\n");
        printf("+  Anagrafica clienti    +\n");
        printf("+  Programma strutture   +\n");
        printf("+   1 - inserisci i dati +\n");
        printf("+   2 - leggi i dati     +\n");
        printf("+   0 - uscita           +\n");
        printf("+                        +\n");
        printf("++++++++++++++++++++++++++\n");
        scanf ("%d", &i);
        printf("prima di return");
        return i;
}

int vuoto(struct anagrafica a[]){  //serve per trovare il primo array vuoto
        int i;
        for(i=0;i<MAX;i++){
                printf("%d\t", i);
                if (a[i].nome[0]=='\0') return i;
        } return 99;
        
}

void main(){
     int scelta;
     int* i;
     struct anagrafica cliente[MAX];

     do {
        scelta=menu();
        *i=vuoto(cliente);     //penso che sia qui l'errore
       if (scelta==1) inserisci (cliente, i);
        if (scelta==2) stampa (cliente, i);
        
     }while (scelta!=0);
     
     
}


Sono quasi sicuro che l'errore sia nel main(), quando assegno *i.

Secondo voi oltre all'errore di segmentazione ho fatto altri errori concettuali?

Grazie

2 Risposte

  • Re: Puntatore ed errore di segmentazione

    Ma perché un puntatore?

    Se restituisci un int allora è un int che devi usare

    int i;

    i = vuoto(....
  • Re: Puntatore ed errore di segmentazione

    Oregon ha ragione nel chiederti perché un puntatore quando basta un int.

    Od ogni modo l'errore concettuale sta nel comprendere che non puoi assegnare un valore intero ad *i se prima non allochi lo spazio di memoria per contenerlo.
    Quando dichiari un puntatore viene riservato spazio per memorizzare un indirizzo di memoria e non spazio per contenere dati.
    Lo spazio che riserverebbe il sistema ad un puntatore ad int è lo stesso che riserverebbe al puntatore ad una struct di centinaia di campi.

    Quindi fermo restando che anche a mio avviso in questo caso basta: int i;
    Ovviamente poi devi utilizzare & per riferirti ad i nelle funzioni che chiami.
    
    /* Se scrivi: */
    int *i = (int *)malloc(sizeof(int));
    /* Eventuali controlli */
    
    Tutto torna a posto.
Devi accedere o registrarti per scrivere nel forum
2 risposte