35 votes

Comment réduire la taille de std::vector ?

Existe-t-il un moyen de redimensionner un std::vector à une capacité inférieure lorsque je n'ai plus besoin de l'espace précédemment réservé ?

61voto

Sébastien RoccaSerra Points 7524

STL efficace, par Scott Meyers, point 17 : utiliser la fonction swap l'astuce pour réduire les capacités excédentaires.

vector<Person>(persons).swap(persons);

Après ça, persons est "rétréci pour s'adapter".

Cela repose sur le fait que vector Le constructeur de copie de l'utilisateur n'alloue que la quantité de mémoire nécessaire pour les éléments copiés.

20voto

Alex Korban Points 7819

Si vous utilisez C++11, vous pouvez utiliser vec.shrink_to_fit() . Dans VS2010 au moins, cela fait l'affaire de l'échange pour vous.

8voto

philsquared Points 13547

Créez un nouveau vecteur, temporaire, à partir du vecteur existant, puis appelez la méthode swap sur le vecteur existant, en lui passant le vecteur temporaire. Laissez le temporaire (maintenant avec l'ancien tampon surdimensionné) sortir de la portée.

Hé presto, votre vecteur a exactement la bonne taille pour son contenu.

Si cela vous semble beaucoup de copies et d'allocations, gardez à l'esprit que c'est ce que fait le vecteur chaque fois qu'il doit réallouer au-delà de sa limite de réservation actuelle.

[Edit] Oui, je viens de dire la même chose que Sébastien en plus de mots. Encore un cas de stackoverflow race-condition ;-)

3voto

jimifiki Points 1435

L'astuce du swap est un moyen efficace de réduire la capacité d'un objet, elle échange le contenu de mon vecteur avec un vecteur nouvellement créé par construction de copie :

vector<Person>(persons).swap(persons);

Notez qu'il n'y a aucune garantie que persons.capacity() ; après l'astuce du swap soit égal à la taille : la capacité de vector(persons) est la capacité que l'implémentation de la bibliothèque réserve aux vecteurs de taille persons.size().

Introduction de C++11 shrink_to_fit() .

shrink_to_fit() ainsi que l'astuce du swap ne garantissent pas que la taille de la capacité soit effectivement réduite à la taille du vecteur.

De toute façon, shrink_to_fit() peut invalider vos itérateurs (si une réallocation se produit) ou non : cela dépend de l'implémentation réelle de la bibliothèque.

Gardez à l'esprit que l'astuce de l'échange nécessite des constructions de copie de person.size() de Person et de person.size() destructions. Le shrink_to_fit() pourrait éviter toute cette copie et pourrait laisser vos itérateurs valides. Pourrait. Mais il se trouve que shrink_to_fit() est implémentée en termes de l'astuce du swap...

-1voto

fulmicoton Points 5389

Vous cherchez un équivalent de QVector::squeeze et je crains qu'elle n'existe pas explicitement dans la STL. Choisissez la réponse de Sébastien si elle est correcte pour votre implémentation STL.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X