2010-04-07 7 views
7

C'est une question embarrassante, mais même la documentation bien fournie fournie avec boost.interprocess n'a pas été suffisante pour que je sache comment pour faire ça.Affectateurs C++, passant spécifiquement les arguments constructeurs aux objets alloués avec boost :: interprocess :: cached_adaptive_pool

Ce que j'est une instance cached_adaptive_pool allocateur, et je veux l'utiliser pour construire un objet, en passant le long des paramètres du constructeur:

struct Test { 
    Test(float argument, bool flag); 
    Test(); 
}; 

// Normal construction 
Test obj(10, true); 
// Normal dynamic allocation 
Test* obj2 = new Test(20, false); 

typedef managed_unique_ptr< 
    Test, boost::interprocess::managed_shared_memory>::type unique_ptr; 

// Dynamic allocation where allocator_instance == cached_adaptive_pool, 
// using the default constructor 
unique_ptr obj3 = allocator_instance.allocate_one() 
// As above, but with the non-default constructor 
unique_ptr obj4 = allocator_instance ... ??? 

Cela peut très bien être un échec de ma part sur la façon d'utiliser objets allocateur en général. Mais dans tous les cas, je ne vois pas comment utiliser cet allocateur spécifique, avec l'interface spécifiée dans cached_adaptive_pool pour passer des arguments constructeur à mon objet.

cached_adaptive_pool a la méthode: void construct(const pointer & ptr, const_reference v) mais je ne comprends pas ce que cela signifie et je ne trouve pas d'exemples l'utilisant.

Ma tête a nagé dans des gabarits toute la journée, donc un coup de main, même si la réponse est évidente, sera grandement appréciée.

Répondre

1

cached_adaptive_pool a la méthode: construction void (pointeur const & ptr, const_reference v) mais je ne comprendre ce que cela signifie et je ne peux pas trouver des exemples de l'utiliser.

Il devrait suivre l'interface de std::allocator, auquel cas allocate() vous donne un morceau approprié de placement mémoire non initialisée et construct() nouveaux appels sur le pointeur donné.

Quelque chose comme:

allocator_instance.construct(allocator_instance.allocate_one(), Test(30, true)); 

ont pas utilisé ces piscines moi-même, bien que. En C++ 0x, les allocateurs devraient être capables d'appeler n'importe quel constructeur, pas seulement le constructeur de copie, donc il se peut que les allocateurs de boost prennent déjà en charge ceci dans une certaine mesure.

a.construct(p, 30, true); //a C++0x allocator would allow this and call new (p) Test(30, true) 
+0

Merci. La première forme est le genre de réponse que je m'attendais, mais j'étais trop confuse et fatiguée pour me réaliser. La seconde forme 'a.construct (p, 30, true)' ne semble pas être prise en charge par cet allocateur de boost spécifique. Assez angoissant, puisque 'cached_adaptive_pool.construct()' renvoie 'void', je dois écrire' allocator_t :: pointer obj = allocator.allocate_one(); allocator.construct (obj, Test (30, true)) '? Je ne suis pas sûr de ce qui est pire, en utilisant deux déclarations pour une opération simple ou en utilisant un placement un peu bizarre nouveau directement. – porgarmingduod

+0

Vous pourriez en faire une fonction distincte. – UncleBens

1

Je suppose que je peux toujours utiliser placement nouvelle syntaxe. L'idée est de déréférencer le pointeur intelligent (dans ce cas offset_ptr) renvoyé par l'allocateur, puis de passer l'adresse brute à new().

unique_ptr obj = new(&(*allocator_instance.allocate_one())) Test(1,true) 

Est-ce la manière idiomatique de faire cela? Il y a tellement d'autres endroits dans boost où un support explicite est fourni pour éviter d'utiliser le placement new, ce qui me fait penser que non. En tout cas, j'accepterai cette réponse si rien de mieux n'est fourni dans un proche avenir.

+0

À quoi sert la séquence '& * ptr'? – UncleBens

+0

Lorsque je l'ai testé, new n'accepterait qu'un pointeur brut, pas un offset_ptr renvoyé par cet allocateur. – porgarmingduod

Questions connexes