【发布时间】:2017-11-16 01:01:45
【问题描述】:
在 C 或 C++ 中,NULL 不只是常量整数 0 吗?如果它是一个常量整数,为什么我们允许分配一些指向值 NULL 的指针?编译器不会说这两种类型不匹配吗?
【问题讨论】:
在 C 或 C++ 中,NULL 不只是常量整数 0 吗?如果它是一个常量整数,为什么我们允许分配一些指向值 NULL 的指针?编译器不会说这两种类型不匹配吗?
【问题讨论】:
常量0 的解释取决于上下文。如果在需要数字的上下文中使用它,则它是数字零。如果在需要指针的上下文中使用它,则将其视为空指针。所以如果你有代码:
int n = 0; // assigns zero
int *p = 0; // assigns null pointer
somefunc((char *)0); // passes null pointer to the function
在 C 中,允许宏 NULL 扩展为整数常量 0 或此类常量转换为 void *。在 C++ pre-11 中,它可以扩展为计算结果为 0 的整数常量。在 C++-11 中,它可以扩展为具有值 0 或类型为 std::nullptr_t 的纯右值(例如 nullptr)的整数文字。
有关 C++ 说明,请参阅 http://en.cppreference.com/w/cpp/types/NULL,有关 C 说明,请参阅 http://en.cppreference.com/w/c/types/NULL。
【讨论】:
nullptr。
(void*)0,因为 C++ 不像 C 那样对 void* 进行隐式转换。
std::nullptr_t 类型的值。 (void*)0 是其中之一吗?
有两个问题:
一个类型可以有一个“特殊的”、带外的、异常值。例如,浮点数的值为NaN。并且指针有一个特殊的非有效指针值,即空指针。
空指针的名称是什么?在 C 中,无论好坏,它的名字都是0。 (如果它的名称是一个单独的关键字,如 null 或 nil,它会避免各种混淆,但语言定义不是这样出来的。)
但是,是的,您是对的,将常量 0 分配给指针变量的能力是一种特殊情况,体现在语言定义中。
【讨论】:
6.3.2.3 指针
...
3 值为 0 的整型常量表达式,或这种类型转换为void *的表达式,称为 空指针常量。66) 如果空指针常量是转换为指针类型后,生成的指针称为空指针,保证与指向任何对象或函数的指针不相等。
66) 宏 NULL 在(和其他头文件)中定义为空指针常量;见 7.19。
指针上下文中的文字0 由编译器特殊处理,并被理解为空指针常量。在您的源代码上下文中,它的行为类似于任何其他零值表达式。
但是,一旦您的代码被转换为机器码,所有出现的空指针常量都将被底层平台用来表示定义明确的 invalid 指针值的任何值替换,无论是0 或 0xFFFFFFFF 或 0xDEADBEEF。
【讨论】: