usar - clase stl c++
Punteros inteligentes en el contenedor como std:: vector? (5)
Cualquier tipo que use con una plantilla de contenedor estándar debe cumplir con los requisitos para ese contenedor. En particular, el tipo debe satisfacer los requisitos para los tipos CopyConstructible y Assignable .
Muchos punteros inteligentes satisfacen estos requisitos y pueden usarse con contenedores estándar, pero std::auto_ptr
no es uno de ellos porque las copias de std::auto_ptr
no son equivalentes a la fuente desde la cual se crearon o asignaron.
Aunque algunas implementaciones del contenedor estándar pueden funcionar con auto_ptr
en algunas situaciones, es peligroso confiar en dichos detalles de implementación.
Estoy aprendiendo sobre punteros inteligentes ( std::auto_ptr
) y simplemente leo here y here que los punteros inteligentes ( std::auto_ptr
) no deben colocarse en contenedores (es decir, std::vector
) porque incluso la mayoría de los compiladores no se quejan y Puede parecer correcto. No hay ninguna regla que indique que los punteros inteligentes no se copiarán internamente (por ejemplo, por clase vector
) y transfieren su propiedad, luego el puntero se convertirá en NULO. Al final, todo será arruinado.
En realidad, ¿con qué frecuencia sucede esto?
A veces tengo vectores de punteros y si en el futuro decido que quiero tener un vector de punteros inteligentes, ¿cuáles serían mis opciones?
Soy consciente de C ++ 0x y las bibliotecas Boost, pero por ahora, preferiría seguir un enfoque de STL.
El problema al que se refiere tiene que ver con auto_ptr, ya que mueve la propiedad en la copia. shared_ptr y unique_ptr funcionan bien con contenedores.
Para las clases que tienen un miembro de auto ptr data, siempre tengo un método de clonación que devuelve un nuevo ptr automático. Luego implemento un método de asignación y un constructor de copia que llama al método de clonación (y nunca el operador de asignación predeterminado de auto ptr). De esta manera puede utilizar la clase de forma segura en contenedores STL.
Sí, realmente no puedes usar std::auto_ptr
con contenedores estándar. std::auto_ptr
copias de std::auto_ptr
no son equivalentes, y debido a que los contenedores estándar (y los algoritmos) pueden copiar sus elementos a voluntad, esto puede complicar las cosas. Es decir, la operación de copiar un std::auto_ptr
tiene un significado distinto al de una mera copia de un objeto: significa transferir una propiedad .
Sus opciones son:
- Utilice la biblioteca de punteros inteligentes Boost . Esta es posiblemente tu mejor opción.
- Usa punteros primitivos. Esto es rápido y seguro, siempre y cuando gestione los punteros correctamente. A veces esto puede ser complejo o difícil. Por ejemplo, tendrá que hacer frente a (evitar) la doble eliminación de problemas por su cuenta.
- Utilice su propio puntero inteligente de recuento de referencias. Eso sería tonto; utilizar un puntero inteligente Boost.
teóricamente, puede usar std::auto_ptr
con contenedores STL si entiende completamente su implementación interna y no hace nada que pueda perder la propiedad de auto_ptr, pero prácticamente es mucho más seguro usar contenedores con ptrs en bruto.
"En realidad, ¿con qué frecuencia sucede esto?" - Es una pregunta muy peligrosa por sí misma. En primer lugar, STL: no es una implementación estándar única, hay muchas. Cada uno puede implementar contenedores de diferentes maneras, por lo que su código altamente sintonizado para evitar todas las minas "auto_ptr en contenedores" puede reventar el cambio a otra implementación de STL. Además, el mantenimiento de su código será muy complicado, cualquier cambio que se vea correctamente en su código puede interrumpir su programa. ¿Cómo puedes recordar eso o forzar a otros mantenedores a recordar? ¿Poner advertencias en cualquier lugar donde puedan ocurrir tales cambios? imposible.
Entonces, conclusión: es solo una mala idea que solo trae dolor de cabeza