Chris
Chris

Reputation:

why destructor is not called implicitly in placement new"?

As referenced in this site... http://www.parashift.com/c++-faq-lite/dtors.html#faq-11.10 But i did not find the reason, why we should explicitly call the desturctor?

Upvotes: 3

Views: 11069

Answers (6)

yesraaj
yesraaj

Reputation: 47900

string *ps = new string("Hello ");

The new in the above statement is called new operator which do two things

  1. Call operator new(allocates necessary memory like malloc) and
  2. Call constructor on raw memory created by operator new to initialize

    delete ps;

Again delete corresponds to

  1. Destruction of object and
  2. Deallocation of memory(i.e, free)

In c++ user is not allowed to call constructor directly,Placement new is used when you have raw memory allocated by some means and wanted to initialize the bits with constructor.Because the memory allocation process did not happen through operator new, delete cannot deallocate the memory.

void someCode()
     {
       char memory[sizeof(Fred)];//memory allocated on stack
       void* p = memory;
       Fred* f = new(p) Fred();//placement new 
       ...
       f->~Fred();   // Explicitly call the destructor for the placed object
     }

Upvotes: 1

Todd Gardner
Todd Gardner

Reputation: 13521

You can think of it as a call to delete, but since you used placement new, you don't want to use delete, as that would attempt to free the memory. If you wanted it to be called automatically, you could use RAII:

// Could use a templated version, or find an existing impl somewhere:
void destroy_fred(Fred* f) {
   f->~Fred();
}

void someCode()
{
   char memory[sizeof(Fred)];
   void* p = memory;
   boost::shared_ptr<Fred> f(new(p) Fred(), destroy_fred);

   // ...

   // No need for an explicit destructor, cleaned up even during an exception
} 

Upvotes: 13

Nick Dandoulakis
Nick Dandoulakis

Reputation: 43110

The example from your link:

void someCode()
 {
   char memory[sizeof(Fred)];
   void* p = memory;
   Fred* f = new(p) Fred();
   ...
   f->~Fred();   // Explicitly call the destructor for the placed object
 } 

"placement new" return the memory offset that we provide. Right after new the compiler adds a call to the ctor ("placement new" is a also a trick to explicity call a ctor).

"memory" is allocated in the stack so we can not delete it.

Upvotes: 3

ChrisW
ChrisW

Reputation: 56113

Normally, an object is created using new, and destroyed when you call delete on the object. However, because 'delete' will also try to free the underlying memory back to the heap, you should never call delete on an object which which was instantiated using placement new.

Nevertheless, (no matter how it was allocated) every object ought to be destroyed (because its destructor might do something important).

Therefore instead of the object's being destroyed using delete, you have to destroy the object yourself, and do so explicitly, by invoking its destructor as shown in the FAQ you cited.

Upvotes: 4

anon
anon

Reputation:

You can't call ordinary delete because that would attempt free the memory, which was not allocated with ordinary new, so you call the destructor directly and then handle the underlying memory allocation depending on the architecture you are using.

Upvotes: 9

Matthew Flaschen
Matthew Flaschen

Reputation: 284796

Normally, newed objects are destructed when delete is called. delete is never called for placement new, so you have to figure out when to destruct the object yourself, and do so explicitly.

Upvotes: 12

Related Questions