Liste STL pour tenir la structure de pointeurs
J'ai une structure appelée vertex et j'ai créé quelques conseils. Ce que je veux faire est d'ajouter ces pointeurs à une liste. Mon code ci-dessous, quand il essaie d'insérer le pointeur dans la liste, crée une erreur de segmentation. Quelqu'un peut-il expliquer ce qui se passe?
#include <iostream>
#include <list>
#define NUM_VERTICES 8
using namespace std;
enum { WHITE, GRAY, BLACK };
struct vertex
{
int color;
int distance;
char parent;
};
int main()
{
//create the vertices
vertex r = {WHITE, NULL, NULL};
//create pointer to the vertex structures
vertex *pr = &r;
//create a list to hold the vertices
list<vertex*> *r_list = new list<vertex*>;
list<vertex*>::iterator it;
r_list->insert(it, pr);
}
il vous manque une valeur de retour de la fonction main
OriginalL'auteur unknown | 2009-07-06
Vous devez vous connecter pour publier un commentaire.
Il y a plusieurs choses mal ici.
Tout d'abord, vous n'êtes pas à l'initialisation de l'itérateur, comme d'autres l'ont dit:
Ce faire et votre code sera bien. Mais votre code est fait d'une mauvaise manière.
Pourquoi êtes-vous de l'allocation de la liste dans le tas? Regardez votre code: vous avez une fuite de mémoire. Vous n'êtes pas à l'appel de
delete r_list
n'importe où. C'est pourquoi vous devez utiliser des pointeurs intelligents (std::unique_ptr
,std::shared_ptr
si vous avez le C++11, boost équivalents autrement :boost::scoped_ptr
etboost::shared_ptr
)Mais mieux encore, faites-le simplement sur la pile:
En outre, l'utilisation de l'itérateur d'insertion est en passe des choses le long chemin. Utilisez simplement pousser() ou push back():
Une autre chose: si votre liste survit après le sommet que vous avez construit, il sera pointant vers quelque chose de valide.
Par exemple:
Une solution consiste à stocker des pointeurs vers les allouées sur la pile des sommets:
Maintenant, même après la fonction de la liste pointe vers un valide allouées sur la pile de vertex. Cela a maintenant le problème que lorsque vous avez fini d'utiliser la liste, vous devez aller à travers la lsit et appel
delete
sur chaque élément. Ce problème est assistée par l'aide de la Boost Pointeur Contenant De La Bibliothèque.La meilleure façon est de simplement stocker les sommets eux-mêmes (plutôt que des pointeurs):
Si vous donnez sommet d'un constructeur, vous pouvez même vous contenter de les construire sur place:
(ceux-ci sont maintenant à l'extérieur de votre problème)
Tout d'abord, la valeur NULL est généralement utilisé uniquement lorsque vous traitez avec des pointeurs. Depuis
distance
etparent
sont pas des pointeurs, l'utilisation0
pour les initialiser, plutôt que deNULL
:Deuxièmement, l'utilisation
constants
plutôt que#define
:Enfin, donner à votre enum un nom, ou de le placer dans un espace de noms:
Espérons que ces aider!
OriginalL'auteur GManNickG
Vous n'avez pas initialisé l'itérateur, il n'est donc pas valable pour insérer avec. Vous pouvez utiliser
r_list->push_back(pr)
au lieu de cela, par exemple.Aussi, les pointeurs de votre liste ne vont pas valide lorsque r est hors de portée. Évidemment, ce n'est pas un problème dans ce cas, puisque c'est dans
main()
, mais je suppose que ce n'est pas l'exemple précis où vous allez utiliser le code, de sorte qu'il peut revenir à vous mordre...Que d'erreur du compilateur semble que vous avez essayé de passer un sommet au lieu d'un sommet* dans la méthode push_back. Mais je peux me tromper...
C'est exact, Tom. Merci. J'ai besoin d'apprendre à mieux lire les messages d'erreurs
Ha, c'est quelque chose qui prend du temps, mais vous obtiendrez de meilleurs à. N'ayez pas peur quand vous voyez long des trucs comme "std::allocator" blah blah (beaucoup de fois vous obtiendrez beaucoup plus de trucs comme ça). Filtre à travers la jonque et d'obtenir de la viande de celui-ci: Vous avez une liste<sommet*>, et l'arg à push_back dit vertex&. :-).
OriginalL'auteur Peter
Tout d'abord, vous n'êtes pas à l'initialisation de
it
à quoi que ce soit. Voulez-vous dire:Aussi, pourquoi êtes-vous de l'initialisation d'un int et char à NULL? Habituellement, les gens utilisent la valeur NULL pour les pointeurs.
Aussi, comment à nommer votre enum et bénéficiant de la sécurité d'énumérations, au lieu de les utiliser comme ints?
Aussi, pas besoin de créer une nouvelle variable pour faire un pointeur vers le sommet. Lorsque vous appelez insérer, vous pouvez passer dans
&r
.Aussi, comme Peter points, pourquoi ne pas simplement utiliser
push_back()
?Votre code devrait ressembler à ceci:
OriginalL'auteur Tom
Vous n'avez pas initialisé
it
, de sorte que vous êtes en insérant au hasard/non initialisée place/pointeur.Normal façons d'ajouter des éléments à une
std::list
inclure ses méthodespush_back
etpush_front
; normalement vous devriez utiliserinsert
seulement si vous avez déjà déterminé par ailleurs, l'endroit précis où vous souhaitez insérer un élément de plus.OriginalL'auteur Alex Martelli