J'ai un tampon 2d que je voudrais passer à un thread avec d'autres valeurs, donc je dois le déplacer dans une structure. Lorsque j'essaie de faire cela, je ne peux pas accéder à nouveau aux valeurs de ma structure et j'ai besoin d'aide.
Voici mon tampon:
main.c:104:47: warning: dereferencing âvoid *â pointer [enabled by default] fprintf(stderr, "%p\n", args->mybuff[0][0]); ^ main.c:104:50: error: subscripted value is neither array nor pointer nor vector fprintf(stderr, "%p\n", args->mybuff[0][0]); ^
Je voudrais stocker un pointeur vers ce tableau 2D dans une structure comme celle-ci:
arg_struct_t *args = malloc(sizeof(arg_struct_t)); args->i = index; args->mybuff = mybuff; fprintf(stderr, "%p\n", args->mybuff[0][0]);
Cependant si j'essaye d'accéder aux valeurs:
typedef struct { int i; void *mybuff; } arg_struct_t;
J'obtiens une erreur:
void* mybuff[8][16384];
Je pense que je dois en dire plus à C99 sur la forme des données que je veux mettre dans ma structure, mais je n'arrive pas à comprendre la bonne façon de le faire. J'apprécie toute aide ou idée ici.
3 Réponses :
Au risque de vous dépasser:
typedef struct { int i; void* mybuff[8][16384]; } arg_struct_t;
Mais la nature générale de void * est un typage générique qui est contraire aux tableaux multidimensionnels. Ce code semble étrange dès que ce type apparaît et il y a probablement autre chose qui ne va pas.
Voici comment stocker l'adresse de mybuff et comment utiliser ce pointeur ultérieurement pour accéder aux valeurs.
int main() { // Starting array int* mybuff[8][16384]; // Save the address of mybuff into 'p'. 'p' is a pointer to (int*)'s int** p = &mybuff[0][0]; // Access the location of row=3, col=4 using 'p' int r = 3; int c = 4; *(p + (r*16384 + c)) = (int*) 123; // 123 is the value to assign return 0; }
Vous devrez donc également transmettre les tailles de ligne et de colonne (8 et 16384) dans votre structure également afin de déréférencer les valeurs. J'ai omis de vérifier dans l'exemple par souci de concision, mais vous devriez le faire dans du vrai code.
Le compilateur ne sait pas quelle adresse en mémoire il doit calculer ici:
typedef void* TBuff[8][16834]; TBuff mybuff; typedef struct { int i; TBuff * mybuff; } arg_struct_t; arg_struct_t *args = malloc(sizeof(arg_struct_t)); args->i = index; args->mybuff = &mybuff; fprintf(stderr, "%p\n", (*args->mybuff)[0][0]);
car args-> mybuff
n'est qu'un pointeur vers void. Pour traiter une telle expression, le compilateur a besoin d'informations sur 1) la taille des éléments du tableau et 2) au moins une des dimensions du tableau.
Le code suivant est plus correct:
args->mybuff[0][0]
@ M.M, pourquoi l'indirection * mybuff ? J'ai seulement remarqué et corrigé maintenant que j'ai utilisé la variable mybuff au lieu du champ args-> mybuff .
masquer un pointeur dans un typedef est une très mauvaise pratique de programmation
Lorsque vous stockez
mybuff
dans la structure, vous perdez toutes les informations de type. Vous devez donc restaurer ces informations en attribuantargs-> mybuff
à un pointeur du type correct, par exemplevoid * (* myptr) [16384] = args-> mybuff
.concernant:
void * mybuff [8] [16384];
Ceci déclare un tampon de 64K pointeurs. C'est ce que tu voulais vraiment. Remarque: sur une architecture 32 bits, cela donne 64k * 4 octets sur la pile. Ce n'est pas une bonne idée de placer autant de données sur la pile