2010-02-11 4 views
1

je définir un vecteur:allocation de mémoire pour _M_start et _M_finish dans un vecteur

vector< int, MyAlloc< int> > *v = new vector< int, MyAllooc< int> > (4); 

MyAlloc est allouant un espace pour seulement 4 ints. La mémoire de _M_start, _M_finish et _M_end_of_storage est allouée sur le tas avant la mémoire pour les 4 ints. Mais qui alloue cette mémoire pour _M_start, _M_finish et _M_end_of_storage? Je veux allouer cette mémoire moi-même. Qu'est-ce que je dois faire? Ne pas utiliser new pour allouer le vecteur.

Répondre

0

Lorsque vous créez le vecteur, il alloue de la place aux variables membres du vecteur (les _M) partout où vous placez le vecteur. Si vous utilisez new, il alloue de l'espace pour ces variables sur le tas. Avec les variables locales, le compilateur leur fait de l'espace dans le cadre de la pile en cours. Si vous faites du vecteur un membre d'une classe, le compilateur leur crée un espace dans la classe conteneur.

Le vecteur utilise ensuite son allocateur pour allouer de la place aux données que vous souhaitez stocker dans le vecteur, en utilisant le mécanisme que l'allocateur est défini pour utiliser.

+0

Ceci est cohérent avec ce que j'ai vu. Ai-je raison de comprendre que l'espace pour (_M's) est alloué par "new" en dehors de MyAlloc? La raison pour laquelle je pose cette question est que malgré un certain nombre d'instructions d'impression, je ne peux pas comprendre où MyAlloc alloue de l'espace pour les _M. Et si l'espace pour _M est alloué par "new" et non MyAlloc, alors comment puis-je prendre le contrôle de cette allocation d'espace? –

+0

Oui, 'MyAlloc' est simplement un objet auxiliaire que le vecteur peut appeler quand il le souhaite. 'new' ne connaît pas les allocateurs, il alloue juste de l'espace pour un vecteur. Vous "prenez le contrôle" de l'allocation des variables membres exactement comme je l'ai dit dans ma réponse: En les allouant où vous voulez. Si vous utilisez 'new' pour allouer le vecteur, les membres du vecteur sont alloués là où' new' décide (sur le tas). Si vous faites du vecteur un membre de classe, tous ses membres sont alloués dans le cadre de cette classe. Si vous utilisez le placement nouveau, ils sont alloués où vous voulez. – jalf

4

En général, vous devez allouer des vecteurs de la pile:

vector< int, MyAlloc< int> > v(4); 

Si vous avez vraiment besoin d'utiliser votre propre allocateur pour cela aussi, allouer la mémoire de l'objet puis appeler le placement nouveau sur elle pour construire le vecteur.

Il est également possible de surcharger l'opérateur global new/delete, mais c'est vraiment compliqué et je ne le recommanderais pas.

+0

Je dois allouer le vecteur sur le tas. Même si je devais utiliser le placement nouveau, la question reste. D'où vient la mémoire pour _M_start, _M_finish etc; puisque même alors je mettrai seulement 4x4 = 16 (en supposant que int est de 4 octets) octets dans le pool de placement. –

+1

Décidez-vous! Souhaitez-vous attribuer vous-même la mémoire (question) ou voulez-vous utiliser la mémoire de tas (commentaire)? Les deux options sont vraiment mutuellement exclusives. – MSalters

+0

Le morceau de code que j'ai mentionné ici se trouve dans une bibliothèque C++ statique qui est utilisée par les programmes C. Je souhaite attribuer moi-même la mémoire. Il se trouve que finalement cette mémoire vient du c-tas par un appel de malloc. –

0

new T alloue sizeof(T) mémoire sur le tas. Dans votre cas, T est std::vector< int, MyAlloc< int> > et comprend des membres comme _M_start.

Si vous souhaitez allouer cette mémoire vous-même, n'appelez pas new.

+0

chose intéressante est que sizeof (* v) donne 12 qui est l'espace pour _M_start, _M_finish, et _M_end_of_storage. Je peux voir à partir de la fonction allocate dans MyAlloc qu'il alloue seulement 16 octets - juste assez pour les ints et excluant les _M_. Si je veux faire cela sur le tas, alors je suppose que je dois utiliser de nouvelles? –

+0

La dernière phrase de cette remarque n'a tout simplement aucun sens. À quoi fait-on référence? – MSalters

1

Les allocations allouent le stockage de données du conteneur, et non les membres de données de conteneur, qui sont alloués normalement. Cela doit être le cas, ou vous ne pourriez pas créer le vecteur en utilisant new ou sur la pile. Ceci est plus clair pour un conteneur basé sur un nœud comme une liste - les nœuds de liste sont alloués par l'allocateur, mais les autres membres de données, y compris les pointeurs vers le premier et le dernier nœuds sont alloués normalement.

+0

Ce que vous dites est logique, mais s'il vous plaît voir ma réponse à l'article précédent. (Poste MSalters.) –