"more effective C + +" ITEM M9 mentions auto_ptr, which is how to release the heap memory allocated for an object when an exception is generated, and avoid repeating the memory release statement.
PS: In this book refers to the function exit problem, function exit will clean up the stack memory, regardless of how to exit gracefully or abnormally exit (only one exception is when you call longjmp. This drawback of Longjmp is the primary reason C + + is the first to support exception handling. Based on this, we encapsulate the deletion of pointers into a stack object. The function exit (exception or normal) will invoke the object's destructor to achieve the purpose of our automatic cleanup of the memory pointed to by the encapsulated pointer.
As a novice, not very understanding, write down, learn to learn.
Ps:c++11 has not advocated the use of auto_ptr, please see link: http://www.cplusplus.com/reference/memory/auto_ptr/
Note: This class template is deprecated as of c++11. Unique_ptr is a new facility with a similar functionality, but with improved security (no fake copy assignments), Adde D Features (deleters) and support forarrays. See unique_ptr for additional information.
The following copy from: http://blog.sina.com.cn/s/blog_7708265a01010lyv.html
1. What is AUTO_PTR?
Auto_ptr is the class template provided by the C + + standard library, which is the owner of this memory, and the Auto_ptr object is initialized to the dynamic memory created by new, and a piece of memory cannot be assigned to two owners at the same time. When the Auto_ptr object life cycle ends, its destructor automatically frees the dynamic memory owned by the Auto_ptr object. Even if an exception occurs, dynamic memory can be freed by the exception stack unwind process. AUTO_PTR does not support the new array.
2. Auto_ptr need to include the header file?
#include <memory>
3. How do I initialize a Auto_ptr object?
1) constructor function
1] Constructs an existing normal pointer to dynamic memory as a parameter
int* p = new int (33);
Auto_ptr<int> API (p);
2] Direct construction of smart pointers
auto_ptr< int > API (new int (33));
2) Copy Construction
Constructs a new smart pointer with an existing smart pointer
auto_ptr< string > Pstr_auto (New String ("Brontosaurus"));
auto_ptr< string > Pstr_auto2 (Pstr_auto); //using Pstr_auto to construct Pstr_auto2
Because a piece of dynamic memory intelligence is owned by a smart pointer, the process of ownership transfer occurs when a copy is constructed or assigned. During this copy construction, Pstr_auto loses ownership of the string memory, and Pstr_auto2 obtains it. When the object is destroyed, the PSTR_AUTO2 is responsible for automatic memory destruction.
3) Assign Value
Constructs a new smart pointer with an existing smart pointer
auto_ptr< int > p1 (new int (1024));
auto_ptr< int > p2 (new int (2048));
P1 = p2;
The object pointed to by P1 is deleted before the assignment. After assignment, P1 has ownership of the int type object. The object value is 2048. P2 is no longer used to point to the object.
4. Does the empty auto_ptr need to be initialized?
The usual pointer, when defined, does not point to any object, and we use NULL to assign it a value. For smart pointers, since the constructor has a default value of 0, we can directly define the empty auto_ptr as follows:
auto_ptr< int > p_auto_int; //Do not point to any object
5. Prevent two Auto_ptr objects from owning the same object (one piece of memory)
Because the ownership of AUTO_PTR is unique, the following code can cause confusion.
int* p = new int (0);
Auto_ptr<int> AP1 (P);
Auto_ptr<int> AP2 (P);
Because AP1 and AP2 both think that pointer p is the tube, and when the destruction attempts to delete p, the behavior of deleting the same object two times is undefined in the C + + standard. So we have to prevent such use of auto_ptr.
6. Be wary of smart pointers as parameters!
1) when passed by value, a local object is produced in the function's scope during the function call to receive the incoming auto_ptr (copy construct), so that the passed-in argument Auto_ptr loses its ownership of the original object, and the object is deleted locally auto_ptr when the function exits. The following example:
void F (auto_ptr<int> AP)
{Cout<<*ap;}
Auto_ptr<int> AP1 (new int (0));
f (AP1);
cout<<*ap1; Error, after the F (AP1) function call, AP1 no longer owns any objects.
2) when referencing or pointers, the above copy process does not exist. However, we do not know what to do with the incoming auto_ptr in the function, and if some of these operations cause it to lose ownership of the object, this could lead to a fatal execution-time error.
Conclusion: The const reference is the bottom line for the intelligent pointer to be passed as a parameter.
7. Auto_ptr cannot initialize to point to non-dynamic memory
The reason is simple, and the delete expression is applied on pointers that are not dynamically allocated, which results in undefined program behavior.
8. Member functions commonly used by auto_ptr
1) Get ()
Returns the memory address of the object that auto_ptr points to. The following example:
int* p = new int (33);
cout << "The Adress of P:" << p << Endl;
Auto_ptr<int> AP1 (P);
cout << "The Adress of Ap1:" << &ap1 << Endl;
cout << "The Adress of the object which AP1 point to:" << ap1.get () << Endl;
The output is as follows:
The Adress of p:00481e00
The Adress of ap1:0012ff68
The adress of the object which AP1 point to:00481e00
The first line is the same as the third row, which is the address of the memory where int resides. The second line is the address of the memory where the class object itself is AP1.
2) Reset ()
Re-sets the object that auto_ptr points to. is similar to an assignment operation, but the assignment operation does not allow a normal pointer to be assigned directly to Auto_ptr, and reset () allows. The following example:
auto_ptr< string > Pstr_auto (New String ("Brontosaurus"));
Pstr_auto.reset (New string ("Long-neck"));
In the example, the pre-reset Pstr_auto has ownership of the "Brontosaurus" character memory, which is first freed. The Pstr_auto then has the ownership of the "Long-neck" character memory.
Note: Reset (0) can release objects and destroy memory.
3) Release ()
Returns the memory address of the object that auto_ptr points to, and frees ownership of the object.
when initializing auto_ptr with this function, you can avoid the case that two Auto_ptr objects have the same object (compared to the Get function).
Examples are as follows:
auto_ptr< string > Pstr_auto (New String ("Brontosaurus"));
auto_ptr< string > Pstr_auto2 (Pstr_auto.get ()); This is two auto_ptr have the same object
auto_ptr< string > Pstr_auto2 (Pstr_auto.release ()); Release can first free up ownership
Attach the implementation code of the AUTO_PTR:
Namespace std{Template<class t> class Auto_ptr {private:t* ap; Public://constructor & destructor-----------------------------------(1) explicit auto_ptr (t* ptr = 0) throw (): AP (PTR) {} ~auto_ptr () throw () {delete AP; }//Copy & Assignment--------------------------------------------(2) auto_ptr (auto_ptr& rhs) throw (): AP (RH S.release ()) {} Template<class y> auto_ptr (auto_ptr<y>& rhs) throw (): AP (Rhs.release ()) {} auto_pt r& operator= (auto_ptr& rhs) throw () {Reset (Rhs.release ()); return *this; } template<class y> auto_ptr& operator= (auto_ptr<y>& rhs) throw () {Reset (Rhs.release ()); return *this; }//Dereference----------------------------------------------------(3) t& operator* () const throw () {return *a P } t* operator-> () const throw () {return AP; }//Helper functions------------------------------------------------(4)//value access t* get () consT throw () {return AP; }//Release ownership t* release () throw () {t* tmp (AP); AP = 0; return TMP; }//Reset value void Reset (t* ptr=0) throw () {if (AP! = ptr) {delete ap; AP = ptr; }}//Special conversions-----------------------------------------------(5) template<class y> struct AUTO_PTR_R EF {y* YP; Auto_ptr_ref (y* RHS): YP (RHS) {}}; Auto_ptr (auto_ptr_ref<t> RHS) throw (): AP (RHS.YP) {} auto_ptr& operator= (auto_ptr_ref<t> rhs) throw () {Reset (RHS.YP); return *this; } template<class y> operator auto_ptr_ref<y> () throw () {return auto_ptr_ref<y> (Release ()); } template<class y> operator auto_ptr<y> () throw () {return auto_ptr<y> (Release ()); } };}
"C + + smart pointer auto_ptr"