C ++ shows the traps for calling destructor and function call traps

Source: Internet
Author: User

C ++ shows the traps for calling destructor and function call traps
I. Reasons for the article

I am writing a project and need to use the multi-tree storage structure. But at some point, I need to destroy this tree, which means that if I create a new tree object, it is very likely that I want to terminate the declaration period of this object somewhere, and will naturally think of displaying the call to the destructor, but it is such a big trap.

Ii. Cause

Let's take a look at the preparations before learning why you should not easily call the destructor.
To understand this problem, we must first understand the concepts of "stack" and "stack.

1) heap: Generally, it is assigned and released by the programmer. If the programmer does not release the heap, the program may be recycled by the OS at the end of the program. Note that it is different from the heap in the data structure. The allocation method is similar to the linked list.

2) stack zone (stack): automatically assigned and released by the compiler, storing function parameter values, and local variable values. The operation method is similar to the stack in the data structure.

We construct objects in a statement body, such as functions, judgments, loops, and directly contained in a pair of "{}" Statement bodies. This object is created in the statement body and destroyed at the end of the statement body. The problem is that such an object isExist on the stack. That is to say, how to manage is completed by the system and cannot be controlled by programmers. Therefore, even if we call the destructor, after the object lifecycle ends, the system will still call the Destructor again to destroy it on the stack to implement the true destructor.

Therefore, if we have a statement to clear heap data in the destructor, calling twice means that the second attempt will be made to clear data that has already been cleared and no longer exists! This is a problem that may cause runtime errors and will not be told during compilation!

Iii. display the consequences of the call

If you want to call the destructor, it is not impossible, but there are three consequences:

1) when explicitly calling, The Destructor is equivalent toCommon member functions;

2) the compiler implicitly calls the destructor. If the memory is allocated, explicit calls to the Destructor will cause repeated calls.An error occurred while releasing the heap memory.;

3) consider an object as occupying some of the stack memory and some of the heap memory (if applied). This makes it easy to understand this problem. When the system implicitly calls the destructor, stack memory is released (the heap memory is manually released). When you explicitly call the destructor, you simply execute the statements in the destructor,Does not release stack memory or destroy objects.

Use the following code:

Example 1:

Class aaa {public: aaa (){}~ Aaa () {cout <"deconstructor" <endl ;}// destructor void disp () {cout <"disp" <endl;} private: char * p ;}; void main () {aaa a;. ~ Aaa (); a. disp ();}

Analysis:

In this case, the first destructor is equivalent to calling a common member function and executing the statements in the function. The second structure is called by the compiler implicitly, added the action to release the stack memory. This class does not apply for heap memory, so the object is completely destroyed, explicitly + the object is destroyed.

Example 2:

Class aaa {public: aaa () {p = new char [1024];} // apply for heap memory ~ Aaa () {cout <"deconstructor" <endl; delete [] p;} void disp () {cout <"disp" <endl;} private: char * p ;}; void main () {aaa a;. ~ Aaa (); a. disp ();}

Analysis:

In this case, the first explicit call of the Destructor is equivalent to calling a common member function, executing the function statement, and releasing the heap memory,Stack memory not released, The object still exists (but it is incomplete and there are insecure factors); the second call to the destructor, the heap memory is released again (an exception is reported here), then the stack memory is released, and the object is destroyed

4. Wonderful mistakes

Under what circumstances will the system automatically call the Destructor? Obviously, if the object is created on the stack, the system will not automatically call it. A common example is new... Delete combination. However, when the delete operation is called, The Destructor is still automatically called. A rare exception is the explicit call of the Destructor before the cache set by delete when the layout is new. This is rare.

After I build on the stack, it shows that the object address still exists when calling the destructor, and you can even insert nodes into it...

In fact, it is best to check whether the data on the stack has been released before the analysis.

////////////////a.hpp#ifndef A_HPP#define A_HPP#include <iostream>using namespace std;class A{private:    int a;    int* temp;    bool heap_deleted;public:    A(int _a);    A(const A& _a);    ~A();    void change(int x);    void show() const;};#endif////////////a.cpp#include "a.hpp"A::A(int _a): heap_deleted(false){    temp = new int;    *temp = _a;    a = *temp;    cout<< "A Constructor!" << endl; }A::A(const A& _a): heap_deleted(false){    temp = new int;    *temp = _a.a;    a = *temp;    cout << "A Copy Constructor" << endl;}A::~A(){    if ( heap_deleted == false){        cout << "temp at: " << temp << endl;        delete temp;        heap_deleted = true;        cout << "Heap Deleted!\n";    }    else {        cout << "Heap  already Deleted!\n";    }    cout << "A Destroyed!" << endl; }void A::change(int x){    a = x;}void A::show() const{    cout << "a = " << a << endl;}//////////////main.cpp#include "a.hpp"int main(int argc, char* argv[]){    A a(1);    a.~A();    a.show();    cout << "main() end\n";    a.change(2);    a.show();    return 0;}
V. Summary

Therefore, do not explicitly call the destructor.

-END-

References

[1] http://blog.csdn.net/todototry/article/details/1483614
[2] http://club.topsage.com/thread-2228024-1-1.html

Copyright statement: you are welcome to repost it. Just specify the source! If you do not like it, please leave a message to explain the reason and step on again. Thank you. I can also know the reason and keep improving !!

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.