C++11中固定大小零初始化数组作为默认参数的问题
为什么我的固定大小数组被初始化成了空指针?
嘿,我刚踩了一个关于C++数组初始化的坑,跟你分享下——我本来以为用g++ -std=c++11 main.cpp编译代码时,像int arr[4]这样的固定大小数组会被零初始化,结果用gdb一调试,发现arr的值居然是0x0(空指针)!
后来我琢磨明白这事儿了:其实这里是C++初始化规则的一个容易混淆的点。当你用{0}去初始化一个声明为int arr[4]的变量时,看起来像是要初始化数组,但实际上编译器这里把它当成了指针的初始化——因为int arr[4]在某些语境下会退化为指针,但更关键的是,这种初始化方式其实触发了一个容易误解的行为:它并没有把数组的每个元素都置零,而是相当于把arr这个“指针”(数组名退化为的指针)初始化成了0,也就是空指针。本质上就和int* arr = {0}的效果一样,只是你声明的是数组类型,但初始化列表的写法让编译器按指针的方式处理了。
要规避这个问题其实很简单:
- 如果是在全局作用域声明数组,那它本来就会被零初始化,不用额外操作;
- 如果是局部作用域,想要把数组的所有元素都置零,你可以直接写
int arr[4] = {};——注意是空的初始化列表,C++11及以后标准会自动把所有元素零初始化; - 也可以用
memset(arr, 0, sizeof(arr));来手动填充,但记得这只对POD类型(比如int)有效; - 或者更明确地写出所有元素的初始化值,比如
int arr[4] = {0, 0, 0, 0};,不过这种写法对于大数组来说不太方便。
内容的提问来源于stack exchange,提问作者Joakim Thorén
相关产品推荐
相关产品推荐

