根据cppreference,nullptr
是一个关键字:
表示指针文字。它是类型的prvalue std::nullptr_t
。存在从 nullptr 到
任何指针类型的空指针值和任何指向成员类型的指针的隐式转换。任何空指针常量都存在类似的转换,包括类型值和
宏。std::nullptr_t
NULL
nullptr
不同类型的值也是如此std::nullptr_t
,而不是int
。它隐式转换为任何指针类型的空指针值。这个神奇的事情发生在你的幕后,你不必担心它的实现。 NULL
但是,它是一个宏,它是一个实现定义的空指针常量。它通常是这样定义的:
#define NULL 0
即一个整数。
这是一个微妙但重要的区别,可以避免歧义。
例如:
int i = NULL; //OK
int i = nullptr; //error
int* p = NULL; //OK
int* p = nullptr; //OK
当你有两个这样的函数重载时:
void func(int x); //1)
void func(int* x); //2)
func(NULL)
调用 1) 因为NULL
是整数。
func(nullptr)
调用 2) 因为nullptr
隐式转换为类型的指针int*
。
此外,如果您看到这样的声明:
auto result = findRecord( /* arguments */ );
if (result == nullptr)
{
...
}
而且你不能轻易找出findRecord
返回的内容,你可以确定它result
一定是指针类型;nullptr
使这更具可读性。
在推断的上下文中,事情的工作方式略有不同。如果你有这样的模板函数:
template<typename T>
void func(T *ptr)
{
...
}
你尝试用以下方式调用它nullptr
:
func(nullptr);
你会得到一个编译器错误,因为nullptr
它的类型是nullptr_t
. 您必须要么显式nullptr
转换为特定的指针类型,要么为func
with提供重载/特化nullptr_t
。
使用 nulptr 的优点:
- 避免函数重载之间的歧义
- 使您能够进行模板专业化
- 更安全、直观和富有表现力的代码,例如,
if (ptr == nullptr)
而不是if (ptr == 0)