Jimm
Jimm

Reputation: 8515

should i call delete or destructor is enough in c++

if within a function, i new up an object, should i call delete on the pointer before exit of the function or would destructor, which would be automatically called after function exits, do the job of delete?

For example,

   void f()
   {
     A * a = new A(); // assume A has destructor defined, which frees any dynamically assigned resources
   }


 OR

  void f()
  {
    A * a = new A();
    delete a;
  }

Are delete and automatic calling of destructor equivalent?

Upvotes: 1

Views: 1582

Answers (5)

Suvarna Pattayil
Suvarna Pattayil

Reputation: 5239

I'll begin with this,

When is a constructor called?

When a object is being created(constructed). MyClass c,d(1); etc.

A constructor is used to initialise the object properly before using it. Allocate necessary dynamic memory etc.

When is a destructor called?

When an object goes out of scope (when you encounter the } brace in which the object was declared). A destructor is automatically invoked when your object goes out of scope.

When you allocate memory dynamically(new), it stays until you explicilty release(delete) it. And what's better than a constructor to ensure some*thing* you want to happen. Since, a destructor is guranteed to be called before the object is destroyed you can call delete on it.

A destructor by default does not do anything to clear the side-effects you might have created in your code. It won't release memory for you.

You know your butler will follow you out of the room. And will only do things you ask him to do. He will clean up your table after you leave if you instruct him to. If you dont' instruct him to do so, you have to make sure you do it urself somewhere or just leave the mess behind

Upvotes: 0

Andy Prowl
Andy Prowl

Reputation: 126562

if within a function, i new up an object, should i call delete on the pointer before exit of the function or would destructor, which would be automatically called after function exits, do the job of delete?

When returning from a function, all the local objects with automatic storage duration are destroyed. If they are of a class type, their destructor gets invoked before the storage they occupied is claimed back. If they are of a non-class type (like int), there is no destructor to invoke.

Here, the only local object with automatic storage duration is the pointer a (beware: not the object pointed to by a!), and pointers are not of a class type. This means that a will be destroyed, and that's it - in particular, the object a points to will not be destroyed.

Therefore, you have to call delete before you leave the function (no matter whether you leave it by doing return or by throwing an exception). In general, you always have to match each call to new with a call to delete, and each call to new[] with a call to delete[].

Since it is easy to forget about calling delete (as it is easy to call it more than once!) after having created an object with new, it is good practice in Modern C++ to use so-called RAII wrappers (such as smart pointers), which are local objects whose destructors are meant to clean up the resources acquired during construction.

For instance:

void foo()
{
    auto p = std::make_unique<A>(); // OK, make_unique() will only be available
                                    // in C++14. Meanwhile, in C++11 you can do:
                                    //
                                    // std::unique_ptr<A> p(new A());

    // Work with p...

    // No memory leak here!
}

In case you are not allowed to use C++11, for instance because your boss says the SW must compile on older versions of your compiler for compatibility reasons, you can always kill your boss use Boost's smart pointer classes such as boost::shared_ptr and boost::scoped_ptr.

Notice, anyway, that you should not perform a dynamic allocation unless you need to. If you do not need it (e.g. if you don't have to share the ownership of that object with any other function), you can simply give your A object automatic storage duration, thus ensuring its destructor will be invoked when it goes out of scope:

void foo()
{
    A a;

    // Work with a...

    // a will be destroyed when returning from foo()
}

Upvotes: 12

Mike Seymour
Mike Seymour

Reputation: 254751

Only automatic objects are destroyed when they go out of scope:

void f() {
    A a;
} // destroyed here

If you dynamically allocate an object with new, then it's your responsibility to deallocate it with delete; otherwise, it will remain allocated forever and you'll leak memory. This can be quite tricky to manage correctly, especially if exceptions might cause you to leave the scope of the pointer.

For that reason, don't use new unless you really have to; and always use shared pointers or other RAII objects to manage the dynamic object for you.

Upvotes: 3

unxnut
unxnut

Reputation: 8839

When you allocate memory dynamically, it does not get deallocated when the variable goes out of scope. You will have to explicitly delete that memory.

Upvotes: 1

giorashc
giorashc

Reputation: 13713

The only thing that will be freed is the pointer variable itself (as it takes memory as well to store the address it points to and its scope is in the function body only). The object the pointer is pointing to is entire in your responsibility, hence you should delete it explicitly as you explicitly allocated it.

Upvotes: 1

Related Questions