Is there any reason to check for a NULL pointer before deleting?
It's perfectly "safe" to delete a null pointer; it effectively amounts to a no-op.
The reason you might want to check for null before you delete is that trying to delete a null pointer could indicate a bug in your program.
Edit
NOTE: if you overload the delete operator, it may no longer be "safe" to delete NULL
Check for NULL before delete in C++ - good practice?
Why is it so?
Ignorance. Some people do not know that delete(NULL);
is not doing anything.
You can not really check if the pointer is really valid. If you delete twice, you are invoking an undefined behavior.
Is it safe to delete a NULL pointer?
delete
performs the check anyway, so checking it on your side adds overhead and looks uglier. A very good practice is setting the pointer to NULL after delete
(helps avoiding double deletion and other similar memory corruption problems).
I'd also love if delete
by default was setting the parameter to NULL like in
#define my_delete(x) {delete x; x = NULL;}
(I know about R and L values, but wouldn't it be nice?)
NULL check before deleting an object with an overloaded delete
No, don't check for null. The standard says that delete (T*)0;
is valid. It will just complicate your code for no benefits. If operator delete
is overloaded it's better to check for null in the implementation of the operator. Just saves code lines and bugs.
EDIT: This answer was accepted and upvoted, yet, in my opinion, it was not very informative. There is one missing piece in all answers here, and, for conscience sake, let me add this last piece here.
The standard actually says in [basic.stc.dynamic], at least since C++03:
Any allocation and/or deallocation functions defined in a C++ program, including the default versions in the library, shall conform to the semantics specified in 3.7.4.1 and 3.7.4.2.
Where the referenced sections, as well as some other places in the standard listed in other answers, say that the semantics of passing a null pointer are a no-op.
Why is it recommended to set a pointer to null after deleting it?
Just so that you know the pointer does not point to anything anymore, and will fail if conditions and other boolean checks:
delete ptr;
ptr = NULL;
if(ptr)
*ptr = 2;
This code will run perfectly fine, although it would cause memory corruption if the pointer was not set to NULL.
Is it necessary to null your pointers after deleting multidimensional dynamic array
Memory leak will not happen in your case , but for Good Practice you need to null your pointer after deleted that pointer , otherwise if you later dereference the same variable, your program will have undefined behavior
"unhandled exception error" may occur.
if(arr)
also not help this kind of case.
so use the null check of every pointer before access the pointer
Is it good practice to NULL a pointer after deleting it?
Setting a pointer to 0 (which is "null" in standard C++, the NULL define from C is somewhat different) avoids crashes on double deletes.
Consider the following:
Foo* foo = 0; // Sets the pointer to 0 (C++ NULL)
delete foo; // Won't do anything
Whereas:
Foo* foo = new Foo();
delete foo; // Deletes the object
delete foo; // Undefined behavior
In other words, if you don't set deleted pointers to 0, you will get into trouble if you're doing double deletes. An argument against setting pointers to 0 after delete would be that doing so just masks double delete bugs and leaves them unhandled.
It's best to not have double delete bugs, obviously, but depending on ownership semantics and object lifecycles, this can be hard to achieve in practice. I prefer a masked double delete bug over UB.
Finally, a sidenote regarding managing object allocation, I suggest you take a look at std::unique_ptr
for strict/singular ownership, std::shared_ptr
for shared ownership, or another smart pointer implementation, depending on your needs.
Deleting a null pointer
delete
will check if the pointer is NULL for you, so you're right that the check isn't needed.
You might also see that some people set the pointer to NULL after it's deleted so that you don't do anything stupid like try and use memory that is no longer yours or stop you from deleting the pointer twice, which will cause an error.
Why is deleting null pointer allowed in C++
The rule is not strictly necessary in that the language could exist without it; it is simply a decision made by the standards committee. The null pointer is not a valid memory address. However, I would like to believe that each decision is made for a reason, and those reasons are worth knowing.
This rule simplifies the management of failure cases and other instances in which a pointer may be null. It is an easy, inexpensive check to make, and it adds appreciable convenience to the language.
For example, if many conditions exist which would result in dynamic memory allocation, but others also exist which will not, it's convenient to be able to just stick a delete
at the end and not worry about it.
// contrived example
void foo(int n) {
char *p = nullptr;
switch(n) {
case whatever:
case something_else:
p = new char[n];
break;
}
// some code...
delete [] p; // look Ma, no check!
}
If delete nullptr
were illegal then every call to delete
would be surrounded by...
if(ptr)
...and that would be lame. Since this would be the norm, an essentially mandatory convention, why not just eliminate the need to check entirely? Why require an extra 5 characters (minimum) for every call to delete
?
Setting pointer to NULL before delete
Double deleting an object can result in the destructor being called twice, so some people favor setting it to NULL
after deletion. This prevents the destructor from being called on memory which could have been reallocated from the pointer's previous memory address.
As shown here though, setting to NULL
before deleting is a memory leak. Fixed code without memory leak:
if( m_pio ) {
delete m_pio;
m_pio = NULL;
}
Note that calling delete on NULL
(or nullptr
in C++11), is legal so you code could just be written as this instead:
delete m_pio;
m_pio = NULL
Related Topics
Deploying Qt Applications in Linux Properly
Why Do You Use Std::Move When You Have && in C++11
Passing a Std::Array of Unknown Size to a Function
Writing Universal Memoization Function in C++11
Difference Between Std::System_Clock and Std::Steady_Clock
C++: Simple Return Value from Std::Thread
Long Long Int VS. Long Int VS. Int64_T in C++
Std::Lock_Guard or Std::Scoped_Lock
What Are the Rules for the "..." Token in the Context of Variadic Templates
How to Project a Point Onto a Plane in 3D
What Is a Non-Trivial Constructor in C++
Memset() or Value Initialization to Zero Out a Struct
How to Use If (Pointer) Instead of If (Pointer != Null)
Getting Libcurl to Work with Visual Studio 2013
How to Write Custom Input Stream in C++