A null pointer is a pointer whose value is not an address of another object, but a null value. A null value is something that does not have any value. A null pointer does not point anything and dereferencing it can cause undefined behaviors.

A null pointer can be created by value initialization as shown below:

int* nptr{};

Apart from value initialization, we can use nullptr to initialize or assign to a null pointer as shown below:

int* nptr{nullptr};

nullptr keyword represents a null pointer literal similar to boolean literals true and false.

As an aside

There is a type which can be used for a variable to store nullptr without using pointer. That type is std::nullptr_t as shown below:

std::nullptr_t p{nullptr};
std::cout << p << "\n";

It is defined in header <cstddef>.

Checking for null pointers

We can use conditionals to check if a pointer is null as shown below:

if (nptr != nullptr)
{
    std::cout << "Not null pointer";
}
else
{
    std::cout << "Null pointer";
}

As integral types can be implicitly converted to boolean type, null pointer also can be implicitly converted to boolean type. A null pointer is false and non-null pointer is true. Thus, the conditional can be changed to:

 if (nptr)
{
    std::cout << "Not null pointer";
}
else
{
    std::cout << "Null pointer";
}

It should print Null pointer.

Using null pointer to deal with dangling pointers

A dangling pointer points to invalid object that does not exist. Dereferencing that pointer leads undefined behavior. We can solve this by using null pointers. As we can check null pointers using conditionals, whenever there is a chance of creating a dangling pointer, we need to assign a null pointer. We can then check if it is a not a null pointer before dereferencing.

There is no automatic way that C++ provides to handle dangling pointers. It is the responsibility of the developer to make sure to assign null pointers to dangling pointers.

Legacy way of creating null pointers

Some old code may have used 0 literal value to create null pointers. This is the only place where an integral literal value is used to initialize a pointer.

int *iptr{0};
std::cout << std::boolalpha << (iptr == nullptr) << "\n";

It should print true.

Tip

std::boolalpha is an io manipulator that makes printing boolean value as true and false. By default, booleans are printed as integral value. 0 for true and other value for false.

Moreover, there is a NULL macro from header <cstddef> which can also be used to initialize a null pointer.

int *pptr{NULL};
std::cout << std::boolalpha << (pptr == nullptr) << "\n";

However, both of these two should be avoided. Instead, use nullptr.

References

  1. https://www.learncpp.com/cpp-tutorial/null-pointers/