2009-12-04 12 views
10

Tradicionalmente, en C++, creaba cualquier dependencia en el constructor y la eliminaba en el destructor.Nombre del patrón para crear en el constructor, eliminar en el destructor (C++)

class A 
{ 
public: 
    A() { m_b = new B(); } 
    ~A() { delete m_b; } 
private: 
    B* m_b; 
}; 

Esta técnica/patrón de adquisición de recursos, ¿tiene un nombre común?
Estoy bastante seguro de que lo he leído en alguna parte pero no puedo encontrarlo ahora.

Editar:
Como muchos han señalado, esta clase es incompleta y realmente debería implementar un constructor de copias y un operador de asignación.
Originalmente, lo dejé intencionalmente porque no era relevante para la pregunta real: el nombre del patrón. Sin embargo, para completar y alentar buenas prácticas, la respuesta aceptada es lo que es.

+5

Mala clase A. Copiar el constructor y el operador de asignación faltan. –

+1

Una solución más simple si no se requiere copia/asignación es derivar de boost :: noncopyable. Le ahorra tener que definir esas dos funciones. (y se asegura de que no se llamen accidentalmente) – jalf

Respuesta

14

La respuesta a su pregunta es RAII (Recursos de adquisición es de inicialización).

Sin embargo, su ejemplo es peligrosa:

Solución 1 Utilice un puntero inteligente:

class A 
{ 
    public: 
    A(): m_b(new B) {} 
    private: 
    boost::shared_ptr<B> m_b; 
}; 

Solución 2: Recuerde la regla de 4:
Si su clase contiene un "puntero RAW Propiedad", entonces necesita anular todos los métodos generados por el compilador.

class A 
{ 
    public: 
    A():    m_b(new B)   {} 
    A(A const& copy): m_b(new B(copy.m_b)) {} 
    A& operator=(A const& copy) 
    { 
     A tmp(copy); 
     swap(tmp); 
     return *this; 
    } 
    ~A() 
    { 
     delete m_b; 
    } 
    void swap(A& dst) throw() 
    { 
     using std::swap; 
     swap(m_b, dst.m_b); 
    } 
    private: 
    B* m_b; 
}; 

Uso el término "Puntero RAW Propio" arriba, ya que es el ejemplo más simple. Pero RAII es aplicable a todos los recursos y cuando su objeto contiene un recurso que necesita administrar ('Propietario de RAW Poiner', Manija de BD, etc.).

+0

¿Por qué su ejemplo es defectuoso?Se asignó al constructor y se desasignó en el destructor –

+5

Debido al constructor de copia generado por el compilador. –

+2

"posee un puntero sin formato" probablemente debería expandirse a "o un manejador de recursos de cualquier otro tipo". Lo mismo aplica para manejadores de archivos, sockets, conexiones a bases de datos o cualquier otro recurso cuya vida útil deba ser administrada. – jalf

19

RAII - Raii

+1

, aunque normalmente usaría un puntero inteligente para hacer la RAII en lugar de codificarla usted mismo –

+4

No necesariamente. Escribir la clase RAII usted mismo le brinda un mejor control sobre la administración de la vida del recurso. Los punteros inteligentes son solo uno de los muchos ejemplos posibles de RAII. El modismo abarca * mucho * más que 'boost :: shared_ptr' – jalf

2

Esta técnica es mejor conocida como RAII - La asignación de recursos es la inicialización. Tiene su propio tag en este sitio.

Alternativa. se han sugerido nombres más intuitivos, en particular:

Cuestiones relacionadas