tags:

views:

532

answers:

10

In my initial basic tests it is perfectly safe to do so. However, it has struck me that attempting to manipulate this later in a function that deletes this could be a runtime error. Is this true, and is it normally safe to delete this? or are there only certain cases wherein it is safe?

+2  A: 

Yes. It should be perfectly fine. "This" is just a pointer. Any pointer will do for delete. The information on how to delete an object is contained in the heap records. This is how IUnknown::Release() is usually implemented in COM objects.

Steve Rowe
+5  A: 

It's safe to delete "this" as long as it's essentially the last operation in the method. In fact several professional level APIs do so (see ATL's CComObject implementation for an example).

The only danger is attempting to access any other member data after calling "delete this". This is certainly unsafe.

JaredPar
+1  A: 

Read for a similiar discussion. Your understanding is right in that it does work, is needed, and can be dangerous since you can't access this afterwards.

hacken
+13  A: 

delete this is legal and does what you would expect: it calls your class's destructor and free the underlying memory. After delete this returns, your this pointer value does not change, so it is now a dangling pointer that should not be dereferenced. That includes implicit dereferencing using the class's member variables.

It is usually found in reference-counted classes that, when the ref-count is decremented to 0, the DecrementRefCount()/Release()/whatever member function calls delete this.

delete this is typically considered very bad form for many reasons. It is easy to accidentally access member variables after delete this. Caller code might not realize your object has self-destructed.

Also, delete this is a "code smell" that your code might not have a symmetric strategy for object ownership (who allocates and who deletes). An object could not have allocated itself with new, so calling delete this means that class A is allocating an object, but class B is later freeing it[self].

cpeterso
Technically, your last paragraph is incorrect. While it is true that an object could not have allocated itself, this doesn't imply where you go next. It does not therefore follow that a different class allocated it. A static factory method on the same class could have done the creation.
Steve Rowe
"delete this is typically considered very bad form for many reasons." i think that is why well designed ref-counted classes do not use delete this; . they use the handle/body idiom. in my opinion, using delete this is almost always a bad idea. (well, i don't know *any* reason - but im being careful)
Johannes Schaub - litb
A: 

delete this can cause an issue when you have subclasses of the object you are deleting. Remember construction starts from top down and deletion starts from bottom up. So if delete this is in the middle of the hierarchy you basically lost all the objects below this particular class.

delete this comes very handy when you are implementing a reference counted object, an example of which is the COM classes.

rptony
What do you mean when you say "you have basically lost all the objects below this particular class? Can you explain this? Perhaps provide an example?
1800 INFORMATION
Your example is only true if you don't use virtual destructor. So in a sense you are totally right, but then again a hirarchy withou virtual destructors is pure evil, so one 'should' never see it happen.
Robert Gould
+3  A: 

Delete this is perfectly legal as others have already mentioned. It is risky for one additional reason that hasn't been mentioned yet - you are assuming that the object has been allocated on the heap. This can be difficult to guarantee, although in the case of reference counting implementations isn't generally a problem.

1800 INFORMATION
Great point. "delete this" should really only be done if you know for certain how the object was created. This usually means having a private constructor of some sort.
Steve Rowe
In my case, it's inside a state machine, so when the current state is done, it makes a new state and replaces the only pointer to it in the state handler and then `delete this`s itself.
Cristián Romo
The "proper" solution is to have a private destructor. The object can then call delete this, but you can not establish a stack based version.
hacken
Ah, I see. Clever.
Cristián Romo
+4  A: 

As stated by others, delete this is a valid idiom but for it to be safe you have to ensure that the object is never instantiated on the stack.

One way to do this is to make both the constructor and the destructor private and enforce object creation through a class factory function which creates the the object on the heap and returns a pointer to it. The class factory can be a static member function or a friend function. Cleanup can then be done through a Delete() method on the object that does the "delete this". COM objects basically work this way except that in addition they are reference counted with the "delete this" occurring when the reference count is decremented to zero.

Bruce Ikin
+4  A: 

but dont do it in the destructor !

...or in constructor :)
Constantin
Yeah, that'd be bad.
Cristián Romo
A: 

Exact Duplicate click here. I had asked the same question.

Vinay
It's not quite a dupe though, you asked what it's uses are, I asked if it's safe. That to me seems like to different questions.
Cristián Romo
Even I have asked same way. Is it safe to call. I have pasted the line from the question - In the destructor there is a statement like "delete this". I think, this call will be recursive. Why it is working?
Vinay
Yes, but you are asking about a specific case, I'm asking in the general case.
Cristián Romo
A: 

Legal Yes
Safe No

Martin York