Dynamic Stack  «Prev  Next»
Lesson 6Using a Destructor
ObjectiveExamine the use of a destructor in the ch_stack class.
Recall that a destructor is member function whose usual purpose is to destroy objects of its class. A destructor name is the class name preceded by a tilde (~).
Destructors are almost always called implicitly, usually at block exit of the block in which the object was declared.
They are also invoked when a delete operator is called on a pointer to an object whose class has a destructor, or where a sub-object of an object being deleted must also be deleted.
Let us augment our ch_stack example with a destructor:
//ch_stack with constructors and destructor
class ch_stack {
public:
   ch_stack();           //default constructor
   explicit ch_stack(int size) :
     max_len(size), top(EMPTY) {'s
        assert(size > 0);
        s = new char[size];
        assert(s);
     }
   ch_stack(const stack& str)   //copy constructor
   ch_stack(int size, const char str[]);
   ~ch_stack() { delete []s; }   //destructor
   .....
private:
   enum   { EMPTY = -1 };
   char*  s;
   int    max_len;
   int    top;
};

The addition of the destructor allows the class to return unneeded heap-allocated memory during program execution. All the public member functions perform in exactly the same manner as before.
The difference is that the destructor will be implicitly invoked upon block and function exit to clean up storage that is no longer accessible. This is good programming practice, and allows programs to execute with less available memory.

Destructors

If the purpose of a constructor is to ensure that every allocated value is properly initialized, then the purpose of a destructor is to ensure that values are properly prepared for their deallocation. A destructor is a member function with the name ~ClassName, no arguments, and no return type. Like constructors, destructors are never directly invoked; instead they will be implicitly invoked when a value is destroyed.
This can occur in the following situations:
  1. At the end of a block, destructors for any local variables will be invoked.
  2. At the end of a function, destructors for any arguments will be invoked.
  3. At the end of a statement, destructors for any named or unnamed temporary variables will be invoked.
  4. When a dynamically allocated value is deleted, the destructor is invoked before the memory is recovered.
  5. When main terminates, destructors for all static local and global values will be invoked.
  6. When an object variable is deleted, destructors for any data fields will be invoked.
  7. When an object variable from a derived class is deleted, destructors for the base class will be invoked.
  8. When an exception is thrown and execution leaves a block, destructors for any local variables will be invoked.

ClassName::~ClassName()
{
statements
}
Example:
String::~String()
{
delete[] buffer;
}

Purpose: Perform any housekeeping tasks that should be performed before an object is deleted.