Asignador personalizado (pool) con ptr compartido de boost


Quiero que los objetos administrados por un shared_ptr se asignen desde un pool, digamos la interfaz del Pool de Boost, ¿cómo se puede lograr esto?

Author: myahya, 2010-05-26

3 answers

Aquí está el código para hacer lo que quieras (probablemente no compile ya que no tengo boost a mano y lo estoy escribiendo desde la memoria):

class YourClass; // your data type, defined somewhere else

boost::object_pool<YourClass> allocator;

void destroy(YourClass* pointer)
{
    allocator.destroy(pointer);
}

boost::shared_ptr<YourClass> create()
{
    // usage of object_pool<??>::construct requires that you have a 
    // YourClass::YourClass(void) defined. If you need to pass arguments
    // to the new instance, you need to do that separately.
    // 
    // for example using a YourClass::Initialize(your,parameters,here) method
    // before returning from this function
    return boost::shared_ptr<YourClass>( allocator.construct(), &destroy );
}

// usage:
boost::shared_ptr<YourClass>  newObject = create();

Implementé esto dos veces, en dos proyectos diferentes. En ambos, las funciones create y destroy estaban sincronizadas (se puede agregar un bloqueo boost::mutex alrededor del uso de allocator) y eran miembros de una clase factory (y la firma de destroy se modificó a void (YourClass*) mediante el uso de boost::bind).

También puede evitar escribir dos funciones adicionales (el destroy y create) enlazando object_pool<YourClass>::destroy directamente en el constructor boost::shared_ptr.

Soy demasiado perezoso para escribir todo eso ahora :).

Editar (moví mi comentario de respuesta aquí para el formato del código):

Para enlazar la función de destrucción:

class ClassFactory
{
    boost::object_pool<YourClass> allocator;
public:
    boost::shared_ptr<YourClass> create()
    {
        return boost::shared_ptr<YourClass>(
            allocator.construct(),
            boost::bind(&ClassFactory::destroy, this, _1) );
    }

    void destroy(YourClass* pointer)
    {
        allocator.destroy(pointer);
    }
};

ClassFactory debe tener una vida útil más larga que la shared_ptr (si se elimina la instancia ClassFactory, el puntero de este pasado a la instancia shared_ptr será inválido y bloqueará su aplicación cuando la shared_ptr elimine la YourClass instancia).

 21
Author: utnapistim,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-06-03 13:20:47

Solución evidente:

Cree su propia función make_shared e imponga el uso de este método a created shared_ptr. Los que se deriven de la Regla serán castigados.

Nota:

Parece haber una confusión con el papel de los shared_ptr. Su función es administrar la memoria que ha asignado, sin embargo, para hacerlo requiere alguna asignación propia (contador y deleter), por lo que puede pasarle un asignador para ellos.

 4
Author: Matthieu M.,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-05-26 08:33:28

Estas son preocupaciones casi ortogonales. shared_ptr no participa en la asignación de objetos.

Donde es está en la eliminación de la memoria ya no se hace referencia. Si ha asignado desde cualquier cosa que no sea el montón predeterminado, necesitará proporcionar un deleter personalizado

 1
Author: philsquared,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 12:34:01