Saturday, 26 January 2013

Destructors in C++

In my last post, I have discussed about Constructors.
Today we will discuss about Destructors.
But before that look at Memory Management.

Memory Management

* Repeatedly creating objects will eat up memory, especially if the object stores vectors or arrays in  
   its private variables.
* Running out of memory may cause your program to crash.
* Sometimes if you run a program many times, it will start to crash.
* It would be nice to have a way to remove objects that we no longer need, so that we can free up memory

Automatic Self-Destruct

When we create a local variable for a function, the memory blocks it used are deallocated. This saves memory.
void fun () 
{
     double a; 
     int b[10];  
     string c;
}

* A
ll variables are destroyed when the program ends.  
* But dynamic arrays are not automatically destroyed. YOU control the memory blocks.
* So clear any dynamic memory when you are done with it.  
  Clean up after yourself!
 void fun() 
 {
       int a* = new int[10];
       delete[] a;
 }

* But what if our function creates a local variable that is a class?
 void fun() 
 {
       MyClass c;
 }

* If the class only uses primitive data types (int, double, char) and built-in classes (string, vector),
   then the compiler will figure out how to destroy it.
* If the class uses dynamic memory (pointers), then it will NOT be destroyed automatically.
* You should write a destructor for the class.

Destructors

* A class destructor frees up the memory taken up by the private variables of the class.
* The standard C++ convention is to call the destructor function:
  ~ClassName( );
* Even the built-in C++ classes follow this standard.
  string s = "Millenium Falcon";         //Let string be a class
  s.~string( );                      //Now s="" (blank)

  vector v(1000);              //Let vector is a class
  v.~vector( );  
              //Clears 1000 memory blocks.

Note that variables v and s still exist, they're just reset to blank.
 cout << s << v.size( );

 Example:
  A trivial class Test that uses dynamic memory. The default constructor creates a dynamic array
 with 100,000 memory blocks.
 class Test 
 {
      public:
           Test();
      private:
           int* p;
 };
 Test::Test() 
 {
      p = new int[100000];
  }

 * The test class has a dynamic array as a private variable. So we should define a destructor 
    ~Test();
* Otherwise every Test we create will continue to eat up memory. This could result in disastrous            situations. like
 void fun () 
{
        int main() 
        {
              Test t; 
              for (int i=0; i<10000; i++)
                    return; 
              fun();
        } return 0;
}

The destructor is actually quite easy.
Test::~Test() 
{
        delete[] ; //Deletes all blocks in array
}

Automatic Self-Destruct
* When a function ends, we don't want its local variables using up memory.
* Primitive data types (int, char, double) are automatically deleted at the end of a routine.
* If a class is equipped with a destructor ~ClassName(); , the object is destroyed automatically when    it goes out of scope, like at the end of a function.
void my_fun (vector v1) 
{
      vector v2 = v1;
      int x = 3;
      return;
 }

* Note v1 is passed by value, so a local copy is created just for the function. The second vector v2 is    a local variable.
* Both v1 and v2 are automatically destroyed when the function ends if there is a  
 ~vector( );(And there is!)
* Destructors also called at end of main routine. This is why it's important to call destructor.
   ~class_name();

This is about destructors...

No comments: