Bonjour,
Code:double ** coef;
pour allouer de la mémoire pour coef, je trouve sur le net le code suivant :
Quelle est l'utilité de (double**) devant malloc?Code:
1
2
3 coef=(double**)malloc(lignes*sizeof(double*));
Merci
Version imprimable
Bonjour,
Code:double ** coef;
pour allouer de la mémoire pour coef, je trouve sur le net le code suivant :
Quelle est l'utilité de (double**) devant malloc?Code:
1
2
3 coef=(double**)malloc(lignes*sizeof(double*));
Merci
EsthétiqueCitation:
Quelle est l'utilité de (double**) devant malloc?
malloc retourne un void*. Si on écrit :
et si on utilise un compilateur un peu râleur, on peut racevoir un joli warning :Citation:
coef=malloc(lignes*sizeof(double*));
"vous déclarez que coef est un double**, et vous essayez d'affecter à coef un void*. Etes-vous sûr(e) que c'est vraiment ce que vous voulez faire ?"
Alors, pour dire au compilateur que, oui, c'est vraiment ce qu'on veut faire, on lui signale que l'adresse retournée par malloc doit être convertie en double**
Ainsi le compilateur nous fait confiance et cela fait toujours un warning en moins.Citation:
coef=(double**)malloc(lignes*sizeof(double*));
C'est inutile (parfois nuisible sur un compilo mal configuré, car ça peut cacher une erreur) et un compilo C respectueux du standard n'est pas censé gueuler:
En C, un pointeur void* peut être converti implicitement en tout autre pointeur (sauf pointeur de fonction)L'errata de la dernière version du K&R ne recommande plus de le mettre.
Note: Il en est différemment en C++, où un cast explicite est nécessaire. Mais même là, le cast le moins permissif (static_cast) suffit.
Ceci permet d'éviter des erreurs.
Déjà c'est un moyen de se souvenir comment utiliser malloc :
Ainsi tu vois bien que tu vas stocker des éléments de type TYPE et que le pointeur doit être de type TYPE *.Code:coef=(TYPE *)malloc( lignes*sizeof(TYPE) );
Il ne te reste alors plus qu'à remplacer TYPE par le type que tu veux stocker (ici double *).
Ensuite, cela permet de bien vérifier que coef est du bon type :
Compilera.Code:int * coef = malloc(lignes*sizeof(double *) );
Il vaut mieux faire ceci :
Ainsi si jamais dans ton code tu modifies le type de coef, tu auras une erreur à chaque endroit où tu as fait un malloc et tu pourras corriger en fonction.Code:int * coef = (double **)malloc(lignes*sizeof(double *) );
Cette syntaxe peut aussi être utilisée dans du code C++ (mais cela reste très exceptionnel et on préférera toujours, en C++, utiliser new ou des containers).
Une autre syntaxe est possible :
Ainsi tu es sûr que tu vas toujours stocker le bon type d'éléments même si tu modifies le type de coef et tu n'auras pas d'erreurs lors du changement de type.Code:coef = malloc(lignes*sizeof( *coef) );
Les deux solutions se valent mais il ne faut surtout pas faire un mix des deux :
Dans la première solution, on pourra utiliser un typedef pour changer le type de coef sans changer le reste du code. Après dans certains cas, il peut être intéressant d'avoir des erreurs pour bien vérifier que le changement du type ne "fausse" pas certains bouts du code (exemple passage de int (valeurs possibles - beaucoup à + (beaucoup-1) cf FAQ C) à unsigned char (valeurs possibles : 0 à 255) ) ainsi avoir des erreurs peut aider à bien revérifier l'ensemble du code.Code:coef = malloc(lignes*sizeof(double *) ); // pas bien !
N.B. Quand je dit "stocker le bon type d'élément", c'est un abus de langage, il faudrait dire allouer l'espace mémoire nécessaire pour stocker lignes TYPE.
Merci pour toutes les réponses.