struct node{
struct node next;
int id;
}
donne "le champ suivant a une erreur de type incomplète".Elément struct suivant, type incomplet
quel est le problème avec cette struct?
struct node{
struct node next;
int id;
}
donne "le champ suivant a une erreur de type incomplète".Elément struct suivant, type incomplet
quel est le problème avec cette struct?
Lorsque vous créez un type de données auto-référentiel, vous devez utiliser des pointeurs pour contourner les problèmes de circularité:
struct node;
struct node {
struct node * next;
int id;
}
... devraient travailler, mais veillez à allouer correctement la mémoire lors de son utilisation.
Pourquoi un pointeur? Considérez ceci: le point d'une définition struct
est de sorte que le compilateur peut comprendre combien de mémoire allouer et quelles parties accéder lorsque vous dites node.id
. Si votre structure node
contient une autre structure node
, combien de mémoire le compilateur doit-il allouer pour un node
donné? En utilisant un pointeur, vous contournez ce problème, car le compilateur sait combien d'espace allouer pour un pointeur.
Le problème est, lorsque le compilateur atteint cette ligne:
struct node{
struct node next; /* << this line */
le compilateur ne fait pas ce qui est savoir struct node
, parce que vous définissez struct node
.
En général, vous ne pouvez pas utiliser un type qui n'est pas défini ou incomplet.
node
pendant qu'il traite sa définition.Essayez ceci:
struct node;
struct node{
struct node *next;
int id;
};
La déclaration forward n'est pas nécessaire car la déclaration de la structure agit comme sa propre déclaration forward. Le problème est entièrement qu'il a essayé de mettre une structure à l'intérieur de lui-même et aurait dû utiliser un pointeur. – JeremyP
Certaines utilisations de types incomplets sont mal formées, par exemple lorsque vous essayez de déclarer un objet de type incomplet. Cependant, vous pouvez déclarer un pointeur sur un type incomplet (par exemple). Dans ce cas, qui est juste ce qu'il faut ici:
struct node{
struct node *next;
int id;
};
Si un struct pourrait contenir une autre instance de son propre type, sa taille serait infinie.
C'est pourquoi il ne peut contenir qu'un pointeur à son propre type.
En outre, à ce stade du code, la taille de la structure est inconnue, de sorte que le compilateur ne pouvait pas savoir combien d'espace à réserver pour cela.
Pour travailler, vous devez écrire:
typedef struct _node{
struct _node* next;
int id;
}node;
Les identifiants commençant par un trait de soulignement sont réservés à l'implémentation. – Flexo
awoodland: uniquement trait de soulignement + lettre majuscule ou double trait de soulignement. – u0b34a0f6ae
En fait, le compilateur * sait * déjà. Le vrai problème est que le 'struct' sera de taille infinie en raison de l'auto-référentialité. La solution consiste à utiliser un pointeur ('struct node * next').;-) –