Pointeur au vecteur vs vecteur de pointeurs vs pointeur au vecteur de pointeurs
Me demandais ce que vous pensez est la meilleure pratique au sujet de vecteurs en C++.
Si j'ai une classe contenant un vecteur de variable membre.
Quand faut-il le vecteur d'être déclarée:
- L'ensemble de l'objet" vecteur membre varaiable contenant des valeurs, c'est à dire
vector<MyClass> my_vector;
- Pointeur sur un vecteur, j'.e
vector<MyClass>* my_vector;
- Vecteur de pointeurs, c'est à dire
vector<MyClass*> my_vector;
- Pointeur de vecteur de pointeurs, c'est à dire
vector<MyClass*>* my_vector;
J'ai un exemple précis dans une de mes classes où je suis actuellement a déclaré un vecteur de cas 4, c'est à dire vector<AnotherClass*>* my_vector;
où AnotherClass est une des classes que j'ai créé.
Puis, dans la liste d'initialisation de mon constructeur, je créer le vecteur à l'aide de nouvelles:
MyClass::MyClass()
: my_vector(new vector<AnotherClass*>())
{}
Dans mon destructeur je ne les suivants:
MyClass::~MyClass()
{
for (int i=my_vector->size(); i>0; i--)
{
delete my_vector->at(i-1);
}
delete my_vector;
}
Les éléments des vecteurs sont ajoutés dans l'une des méthodes de ma classe.
Je ne sais combien d'objets seront ajoutés à mon vecteur à l'avance. C'est décidé, quand le code s'exécute, basé sur l'analyse d'un fichier xml.
Est-ce une bonne pratique? Ou si le vecteur lieu d'être déclaré comme l'un de l'autre des cas 1, 2 ou 3 ?
Quand utiliser quel cas?
Je sais que les éléments d'un vecteur doit être pointeurs si ils sont des sous-classes d'une autre classe (polymorphisme). Mais doit pointeurs être utilisé dans tous les autres cas ?
Merci beaucoup!!
source d'informationauteur Lisa
Vous devez vous connecter pour publier un commentaire.
Généralement la solution 1 est ce que vous voulez puisque c'est le plus simple en C++: vous n'avez pas à prendre soin de la gestion de la mémoire, C++ fait tout cela pour vous (par exemple, vous n'avez pas besoin de fournir toute destructeur de l'époque).
Il y a des cas où cela ne fonctionne pas (plus particulièrement lorsque l'on travaille avec polymorphe des objets), mais en général c'est la seule bonne façon.
Même lorsque l'on travaille avec polymorphe objets ou lorsque vous avez besoin de tas objets alloués (pour quelque raison que ce soit) les pointeurs sont presque jamais une bonne idée. Au lieu de cela, utiliser un pointeur intelligent ou contenant des pointeurs intelligents. Moderne compilateurs C++ fournir
shared_ptr
à partir de la prochaine norme C++. Si vous utilisez un compilateur qui n'ont pas encore de cela, vous pouvez utiliser le la mise en œuvre de Boost.Certainement le premier!
Vous utilisez vecteur pour sa gestion automatique de la mémoire. À l'aide d'un pointeur brut pour un vecteur signifie que vous n'obtenez pas de gestion automatique de la mémoire plus, ce qui ne fait pas de sens.
Que pour le type de valeur: tous les conteneurs fondamentalement assumer de valeur de type sémantique. Encore une fois, vous auriez à faire la gestion de la mémoire lors de l'utilisation de pointeurs, et c'est le vecteur le but de le faire pour vous. C'est également décrit dans l'article 79 du livre C++ Normes De Codage. Si vous avez besoin d'utiliser le partage de la propriété ou de la "faiblesse" des liens, utilisez le pointeur intelligent à la place.
La suppression de tous les éléments dans un vecteur à la main est un anti-modèle et viole l'idiome RAII en C++. Donc, si vous devez stocker des pointeurs vers des objets dans un
vector
mieux l'utilisation d'un pointeur intelligent' (par exempleboost::shared_ptr
) afin de faciliter la ressource destructions.boost::shared_ptr
, par exemple, appelledelete
automatiquement lorsque la dernière référence à un objet est détruit.Il n'est également pas nécessaire d'allouer
MyClass::my_vector
à l'aide denew
. Une solution simple serait:En supposant
whatever
est un type pointeur intelligent, il est pas de travail supplémentaire à faire. Ça y est, toutes les ressources sont automatiquement détruits lors de la durée de vie d'unMyClass
instance se termine.Dans de nombreux cas, vous pouvez même utiliser une plaine
std::vector<MyClass>
- c'est lorsque les objets dans le vecteur sont sans danger pour la copie.Dans votre exemple, le vecteur est créé lorsque l'objet est créé, et il est détruit lorsque l'objet est détruit. C'est exactement le comportement que vous obtenez lors de la prise de la
vector
un membre normal de la classe.Aussi, dans votre approche, vous allez courir dans des problèmes lors de la réalisation de copies de votre objet. Par défaut, un pointeur seraient le résultat d'une copie à plat, ce qui signifie que toutes les copies de l'objet serait de partager le même vecteur. C'est la raison pour laquelle, si vous gérez manuellement les ressources, vous avez généralement besoin Les Trois Grands.
Un vecteur de pointeurs est utile dans le cas des objets polymorphes, mais il existe des alternatives à considérer:
boost::ptr_vector
.boost::shared_ptr
ou d'un vecteur deboost::ref
.Un pointeur vers un
vector
est très rarement utile - unvector
est bon de le construire et détruire.Pour les éléments dans le
vector
il n'y a pas de bonne réponse. Combien de fois levector
changement? Combien coûte-t-il de copier-construire les éléments de lavector
? Faire d'autres conteneurs avez des références ou des pointeurs vers lesvector
éléments?Comme une règle du pouce, j'irais avec pas de pointeur jusqu'à ce que vous voir ou mesure que la copie de vos cours est cher. Et bien sûr, le cas que vous avez mentionné, dans lequel vous stockez les différentes sous-classes d'une classe de base dans la
vector
exigera des pointeurs.Un comptage de référence de pointeur intelligent comme
boost::shared_ptr
sera probablement le meilleur choix si votre conception de l'sinon vous obliger à utiliser des pointeurs commevector
éléments.Réponse complexe : elle dépend.
si votre vecteur est partagé ou a un cycle de vie différent de la classe qui l'intègre, il pourrait être préférable de le garder comme un pointeur.
Si les objets que vous faites référence n'ont pas (ou ont cher) copie des constructeurs , alors il est préférable de garder un vecteur de pointeur. Dans le cas contraire, si vos objets utiliser la copie superficielle, à l'aide de vecteur d'objets vous empêcher de fuite...
Il dépend. Dans le doute que ce soit de choisir de la déclaration de 1 ou 3, de penser comment feriez-vous déclarer un objet de ce type. Lorsque vous décidez d'utiliser le nombre 1 ou 2, numéro 1 est généralement le bon choix, car un vecteur est un récipient avec de la non-correction de la tailledonc vous n'avez pas besoin de le changer au moment de l'exécution.