J'ai du mal à comprendre comment affecter de la mémoire à un double pointeur. Je veux lire un tableau de chaînes et le stocker.
char **ptr;
fp = fopen("file.txt","r");
ptr = (char**)malloc(sizeof(char*)*50);
for(int i=0; i<20; i++)
{
ptr[i] = (char*)malloc(sizeof(char)*50);
fgets(ptr[i],50,fp);
}
au lieu de cela, je viens d'attribuer un grand bloc de mémoire et stocker la chaîne
char **ptr;
ptr = (char**)malloc(sizeof(char)*50*50);
cela serait-il faux? Et si oui pourquoi?
Votre deuxième exemple est faux car, théoriquement, chaque emplacement de mémoire ne contiendrait pas un char*
mais plutôt une char
. Si vous modifiez légèrement votre façon de penser, cela peut vous aider:
char *x; // Memory locations pointed to by x contain 'char'
char **y; // Memory locations pointed to by y contain 'char*'
x = (char*)malloc(sizeof(char) * 100); // 100 'char'
y = (char**)malloc(sizeof(char*) * 100); // 100 'char*'
// below is incorrect:
y = (char**)malloc(sizeof(char) * 50 * 50);
// 2500 'char' not 50 'char*' pointing to 50 'char'
À cause de cela, votre première boucle serait comment vous faites en C un tableau de tableaux de caractères/pointeurs. L'utilisation d'un bloc de mémoire fixe pour un tableau de tableaux de caractères est acceptable, mais vous utiliseriez un seul char*
plutôt qu'un char**
, car vous ne disposeriez d'aucun pointeur dans la mémoire, mais simplement de char
s.
char *x = calloc(50 * 50, sizeof(char));
for (ii = 0; ii < 50; ++ii) {
// Note that each string is just an OFFSET into the memory block
// You must be sensitive to this when using these 'strings'
char *str = &x[ii * 50];
}
je vais donner un exemple, ce qui pourrait effacer le doute,
char **str; // here its kind a equivalent to char *argv[]
str = (char **)malloc(sizeof(char *)*2) // here 2 indicates 2 (char*)
str[0]=(char *)malloc(sizeof(char)*10) // here 10 indicates 10 (char)
str[1]=(char *)malloc(sizeof(char)*10) // <same as above>
strcpy(str[0],"abcdefghij"); // 10 length character
strcpy(str[1],"xyzlmnopqr"); // 10 length character
cout<<str[0]<<endl; // to print the string in case of c++
cout<<str[1]<<endl; // to print the string in case of c++
or
printf("%s",str[0]);
printf("%s",str[1]);
//finally most important thing, dont't forget to free the allocated mem
free(str[0]);
free(str[1]);
free(str);
Un double pointeur est juste un pointeur sur un autre pointeur. Donc, vous pouvez l'affecter comme ceci:
char *realptr=(char*)malloc(1234);
char **ptr=&realptr;
Vous devez garder à l'esprit l'emplacement de stockage de votre pointeur (dans cet exemple, le pointeur double pointe sur une variable de pointeur de la pile et est donc invalide après le retour de la fonction).
autre moyen plus simple de mémoriser
Cas 1 :
étape 1: char * p;
étape -2: s'il vous plaît lire comme ci-dessous
carbonisé (* p); ==> p est un pointeur sur un caractère
maintenant, il vous suffit de faire malloc pour le type (étape 2) sans accolades
c'est-à-dire, p = malloc (sizeof (char) * some_len);
Cas -2:
étape 1: char ** p;
étape 2 :
veuillez le lire comme ci-dessous
char * (* p); ==> p est un pointeur sur un caractère *
maintenant, il vous suffit de faire malloc pour le type (étape 2) sans accolades
c'est-à-dire p = malloc (sizeof (char *) * some_len);
Cas -3:
Personne ne l'utilise mais juste pour des raisons d'explication
char *** p;
lisez-le comme
caractère ** (* p); ==> p est un pointeur sur un caractère ** (et pour cette vérification cas 2 ci-dessus)
p = malloc (sizeof (char **) * some_len);
char **ptr;
fp = fopen("file.txt","r");
ptr = (char**)malloc(sizeof(char*)*50);
for(int i=0; i<50; i++)
{
ptr[i] = (char*)malloc(sizeof(char)*50);
fgets(ptr[i],50,fp);
}
fclose(fp);
peut-être votre faute de frappe mais votre boucle devrait être de 50 au lieu de 20 si vous recherchez une matrice 50 x 50. De même, après l’allocation de mémoire mentionnée ci-dessus, vous pouvez accéder au tampon sous la forme ptr [i] [j], c’est-à-dire au format 2D.
En ajoutant à la réponse de Pent, comme il l’a bien fait remarquer, vous ne pourrez plus utiliser ce double pointeur une fois la fonction retournée, car elle pointera sur un emplacement mémoire de la fiche d’activation de la fonction qui est désormais obsolète revenu). Si vous souhaitez utiliser ce double pointeur après le retour de la fonction, vous pouvez procéder comme suit:
char * realptr = (char *) malloc(1234);
char ** ptr = (char **) malloc(sizeof(char *));
*ptr = realptr;
return ptr;
Le type de retour de la fonction doit évidemment être char **
pour cela.