0

I'm totally new to C++. I would like to ask about the following.

If a member variable is dynamically allocated in the constructor. Should it always be deleted in destructor? If so, then how is the variable's lifetime "elongated"? If not, how should memory leak be handled otherwise?

I couldn't find any source to address this issue explicitly.

D.Badawi
  • 175
  • 1
  • 13
  • 3
    For a dynamically allocated data member you need to take charge of copying and moving. Apart from that one possibility is to delete in destructor. But instead preferentially use a smart pointer like e.g. `std::unique_ptr` (better yet, use a standard library container, if possible). – Cheers and hth. - Alf May 25 '16 at 10:47
  • What you need are the smart pointers. There are some predefined smart pointers in C++ library. either use them or design your own. – The Philomath May 25 '16 at 10:52
  • So if I use a smart pointer, do I still need to use a move constructor? – D.Badawi May 25 '16 at 11:21
  • @D.Badawi: If you use smart pointers, you don't need to **write** a move constructor. There might still be places where you need to tell the compiler it's OK to **use** the default move constructor. The reason is that moving alters the source object. The compiler will only do so if it's safe, either because it sees it's safe or because you told it so. – MSalters May 25 '16 at 11:40
  • @D.Badawi: It turns out that it's risky to **directly** have multiple dynamically allocated members. E.g. don't have two `int*` arrays as members. However, it is fine to have 2 `std::vector` members. They each wrap a single dynamically allocated `int*` array, and both have a dedicated `std::vector::~vector` to clean up that single allocation. The precise reason is complicated to explain in a comment, but roughly speaking your destructor is not be called if your constructor fails to allocate the **second** resource, which means it cannot clean up the **first** resource. – MSalters May 25 '16 at 11:51

3 Answers3

3

Reasons to allocate a member dynamically are

  • The size of an array may be non-constant
  • The member could be very large, such that there is not enough memory on the stack
  • The member is polymorphic, as commented by MSalters

But, as Alf already pointed out in a comment, it is preferable to use a smart pointer. This has the advantage that you don't need to explicitly delete that member in the destructor, and in the case of a shared_ptr, you can elongate the liftime as needed, the smart pointer takes care of the destruction.

alain
  • 11,939
  • 2
  • 31
  • 51
  • @D.Badawi as alain has wrote, smart pointers are preferred. Additional information you can find [here](http://www.cplusplus.com/reference/memory/). Unfortunately most of them is available from C++11. – Marcin Kajzler May 25 '16 at 11:00
  • 1
    Third reason: The member has a polymorphic type, e.g. either a `Derived1` or a `Derived2`, so you define its type as `std::unique_ptr member;`. – MSalters May 25 '16 at 11:42
2

Should it always be deleted in destructor?

Not a necessity - you can free up the memory as soon as the work is done by some other function, if you are sure it won't be used any further. But, you must anyway call this destruction routine from destructor also to avoid memory leak. Ideally, you'd also need to provide another function for ReAllocate the memory.

In short, it all depends on your class and what are you implementing.

Ajay
  • 18,086
  • 12
  • 59
  • 105
1

Let me take some post-modern approach and say "you don't have to worry about it anymore"

use unique_ptr if only the creating-object is incharge of that resource, use shared_ptr if many objects share that resource. use STL containers for all other possible uses.

use new and delete only if you're writing something extremely low-level or implementing a container from scratch. for all other cases, view dynamic memory allocation (via malloc and new) as deprecated.

David Haim
  • 25,446
  • 3
  • 44
  • 78