PDA

Visualizza la versione completa : [C] Array bidimensionale e realloc


dab82
29-03-2007, 01:56
ragazzi ho un problema con questa funzione...mi da un errore di segmentazione nel main perkè evidentemente non funziona bene il realloc. Inoltre non passa all'esterno l'indirizzo effettivo di B in quanto ha un valore diverso dall'interno all'esterno.



void no_border (int m, int n, int **A, int **B, int *k)
{
int i,j;

// Allocazione dinamica di COORDINATE (creazione di un vettore bidimensionale di dim iniziale 1x2)

//Alloca le righe
B=(int **)malloc(1*sizeof(int *));
//Verifica allocazione righe
if (B == NULL) {
printf("MATRICE B - Allocazione righe fallita: memoria insufficiente");
exit(1);
}
//Alloca le colonne
for (i=0; i<1; i++){
*(B+i)=(int *)malloc(2*sizeof(int));
//Verifica allocazione colonne
if (*(B+i) == NULL) {
printf("MATRICE B - Allocazione colonne fallita: memoria insufficiente");
exit(1);
}
}
//analizza gli elementi della matrice non di bordo
for (i=1; i<m-1; i++){
for (j=1; j<n-1; j++){
if (*(*(A+i)+j) > *(*(A+i-1)+j)){
if (*(*(A+i)+j) > *(*(A+i)+j+1)){
if (*(*(A+i)+j) > *(*(A+i+1)+j)){
if (*(*(A+i)+j) > *(*(A+i)+j-1)){
//assegnazione degli indici dell'elemento
*(*(B+(*k))+0)=i;
*(*(B+(*k))+1)=j;
//incrementa l'indice-dimensione dell'array B
*k=*k+1;
//rialloca l'array B espandendolo a k righe
B=(int **)realloc(B,*k*sizeof(int*));
//alloca i vettori colonna
*(B+(*k))=(int *)malloc(2*sizeof(int));
/************************************
//inizializzazione k-esima riga creata per il realloc succ
*(B+(*k)) = NULL;
//allocazione delle ripettive colonne (REALLOC=MALLOC)
*(B+(*k))=(int *)realloc(*(B+(*k)),2*sizeof(int));
*************************************/
}
}
}
}
}
}
printf("indirizzo di memoria interno di COORDINATE=%d",B);
}

andbin
29-03-2007, 09:33
Originariamente inviato da dab82
ragazzi ho un problema con questa funzione...mi da un errore di segmentazione nel main perkè evidentemente non funziona bene il realloc. Inoltre non passa all'esterno l'indirizzo effettivo di B in quanto ha un valore diverso dall'interno all'esterno.Non è un problema di allocazione dell'array bidimensionale (che tecnicamente è corretta). Il problema è dovuto al fatto che l'array principale lo assegni a B, che è una copia del puntatore passato dal chiamante. Ciò che assegni a B non tocca minimamente la variabile passata dalla funzione chiamante! In pratica non hai capito bene come gestire la restituzione dell'array.

Hai 2 possibilità:

a) Far ritornare un int**


int** no_border (......)
{
int **B;

B=(int **)malloc(1*sizeof(int *));

.....
return B;
}

b) Passare alla funzione un puntatore a puntatore a puntatore a int (int***).


void no_border (...., int*** pB, ...)
{
*pB=(int **)malloc(1*sizeof(int *));

...
}


Inoltre ti segnalo alcune cose:

1) Invece di fare *(B+i) fai semplicemente B[i] e invece di fare *(*(B+(*k))+0) fai semplicemente B[*k][0]. Certo ... così facendo hai sicuramente dimostrato di sapere l'aritmetica dei puntatori :D , ma fare B[i] e B[*k][0] è decisamente più chiaro e dimostra più intelligenza ....

2) Fare un exit(1); all'interno di una funzione in caso di errore è sicuramente molto brutto e certamente discutibile. La tua funzione dovrebbe ritornare una informazione sullo stato successo/fallimento, non certo terminare di brutto! Nel caso a) detto sopra puoi ritornare un puntatore NULL se fallisce, nel caso b) potresti ritornare un int 0 o 1.

In ogni caso una funzione fatta "bene" dovrebbe fare in modo che il chiamante possa conoscere l'esito della funzione. E la funzione, sopratutto per quanto riguarda le allocazioni di memoria, dovrebbe funzionare con un concetto del tipo: o tutto o niente. Cioè se ha successo, alloca quello che deve allocare, se ha fallito in qualcosa non deve allocare nulla (e deallocare cioè che eventualmente aveva già allocato).

dab82
31-03-2007, 14:08
Avevo intuito che era un problema di scambio di parametri...ma avevo provato e mi dava un errore che poi misteriosamente è scomparso...mah...il Dev...cmq mille grazie per le dritte e i consigli...

Loading