我们如何知道默认情况下指针未初始化为NULL? 还有一个针对Why aren't pointers initialized with NULL by default?的类似问题 仅用于检查,这是一个非常简单的代码,仅用于查看默认情况下指针是否设置为NULL。
#include <iostream>
using namespace std;
int main()
{
int* x;
if(!x)
cout << "nullptr" << endl;
return 0;
}
在输出中,我收到了nullptr消息。我很高兴有人可以澄清这一点。
答案 0 :(得分:5)
我们如何知道默认情况下指针未初始化为NULL?
因为我们知道该标准说默认初始化指针如果具有自动或动态存储,则具有不确定的值。来自标准的引文(草稿):
[dcl.init]如果未为对象指定初始化程序,则该对象将被默认初始化。当存储对象时 获得具有自动或动态存储持续时间的对象,该对象具有不确定值,如果 没有对该对象执行初始化,该对象将保留一个不确定的值,直到该值 被替换。 ...
进一步:
[dcl.init]要默认初始化T类型的对象的意思是:
-如果T是一种(可能具有cv资格的)类类型[指针不是一个类,所以我们不在乎]
-如果T是数组类型[指针不是数组,那么我们不在乎]
-否则,不执行初始化。
我没有初始化就声明了一个char(也就是int)指针,并且得到了空指针。
读取不确定的值具有不确定的行为。来自标准的引文(草稿):
[dcl.init] ...如果评估产生不确定的值,则行为未定义,但 以下情况:[此处不适用的情况]
答案 1 :(得分:1)
您链接到的问题专门处理具有本地存储持续时间的变量,因此我假设您也引用了这些变量。
如果您自己不进行初始化,则此类变量不会初始化,因此它们会获得之前在其内存位置中写入的内容的值(标准措辞:它们的值是“不确定的”)–但是,没有任何反对的说法这个记忆已经 为零–完全是偶然的!
您可以尝试以下操作:
void test()
{
int* p; // uninitialized
std::cout << p << std::endl; // undefined behaviour!!!
// (that's what you most likely did already...)
// now something new: change the memory...
p = reinterpret_cast<int*>(static_cast<uintptr_t(0xaddadaad));
}
int main()
{
test();
// again something new: call it a SECOND time:
test();
}
由于这是未定义的行为,因此根本无法保证您将获得任何有意义的输出-机会是,尽管第一个函数调用的内存在第二个函数中被重用并且您可能符合以下条件:
00000000
addadaad
因此,即使在程序启动时仅发生了全部为零的内存,它也可能与程序运行时的稍后时间有所不同...