Article 13: Managing Resources with objects
Suppose you have the following code:
investment* createinvestment (); // returns a pointer to a dynamically allocated object within the investment inheritance system, where the caller is responsible for deleting it void func () { investment* PINV = Createinvestment (); // Call the Factory function ..... delete pinv; // releases the object that PINV refers to}
The code above may cause the object to be deleted from the PINV pointer, causing a resource leak to occur.
(1) "..." in the area of an prematurely concluded return statement;
(2) The delete action is within a loop, and the loop ends prematurely due to a continue or goto statement;
(3) "..." in the area where the statement throws an exception;
Solution: Put resources in the object, we can rely on C + + "destructor automatic call mechanism" to ensure that the resources are released . The auto_ptr provided by the standard library is a specially crafted product designed to address this situation. Auto_ptr is a class pointer (Pointer-like) object, the so-called "smart pointer" whose destructor automatically calls delete on the object it refers to. As follows:
void func () { std::auto_ptr<Investment> PINV (Createinvestment ()); ..... // Call the factory function to automatically delete the PINV} through the auto_ptrdestructor
Analytical:
1. Once the resource has been acquired, put it in the management object immediately. In fact, the concept of " managing resources with Objects " is often referred to as "the timing of resource acquisition is the time of initialization" (Resource acquisition is initialization; RAII). Each resource is immediately placed into the management object while it is acquired.
2. Management objects use destructors to ensure that resources are freed. Even if the destructor throws an exception, clause 08 also gives a solution.
Here is a brief introduction to " Smart pointers ":
Auto_ptr uses the "ownership" approach to manage objects, that is, the assignment of auto_ptr, and the copy operation will take ownership of the object directly, so be careful not to have multiple auto_ptr point to the same object at the same time.
The alternative to auto_ptr is the "Reference Counting Wisdom Pointer" (reference-counting smart pointer; RCSP), which is also a smart pointer, keeps track of how many objects are pointing to a resource and automatically deletes the resource when no one points to it. TR1 's tr1::shared_ptr (clause 54) is a RCSP. The above code can be modified as follows:
void func () { ... Std::tr1::shared_ptr<Investment> PINV (Createinvestment ()); ..... // Call the factory function to automatically delete the PINV} through the shared_ptrdestructor
Note: The above auto_ptr and tr1::shared_ptr are simply examples of "object management resources" used in these terms. At the same time, Createinvestment returns an "unprocessed pointer" (raw pointer) is simply a death invitation to a resource leak, one in which the caller easily forgets to call delete on the pointer, and second, even if you want to use a smart pointer, It is also possible to forget to store the return value of Createinvestment in a smart object. Therefore, Clause 18 provides a workaround: make createinvestment return a smart pointer . Such as:
Std::tr1::shared_ptr<investment> createinvestment ();
This forces the customer to store the return value inside a tr1::shared_ptr.
So:
1. To prevent resource leaks, use the Raii object, which obtains resources in the constructor and frees the resources in the destructor.
2. The two commonly used RAII classes are auto_ptr and tr1::shared_ptr respectively. The latter is usually a better choice because its copy behavior is more intuitive. If you select Auto_ptr, the copy action will cause it (copied) to point to null.
Article 14: Beware of copying behavior in resource management classes
Suppose you have the following code
The compiler can secretly create a default constructor for class
Effective c++--resource Management (iii)