在堆栈与堆中没有构造函数的结构/类的初始化
initialization of structs/classes without constructors in stack vs heap
我想知道C 中没有默认构造函数的Zeroing-Out-Out-Out-Out结构(或类)规则。
尤其是,如果将存储在堆栈中(例如,作为局部变量),它们是不可初学的,但是如果在堆上分配,则它们将被零置化(用GCC 4.9.1进行测试)。保证这是便携式?
示例程序:
#include <iostream>
#include <map>
using namespace std;
struct X {
int i, j, k;
void show() { cout << i << " " << j << " " << k << endl; }
};
int fib(int i) {
return (i > 1) ? fib(i-1) + fib(i-2) : 1;
}
int main() {
map<int, X> m;
fib(10); // fills the stack with cruft
X x1; // local
X &x2 = m[1]; // heap-allocated within map
X *x3 = new X(); // explicitly heap-allocated
x1.show(); // --> outputs whatever was on the heap in those positions
x2.show(); // --> outputs 0 0 0
x3->show(); // --> outputs 0 0 0
return 0;
}
编辑:删除"或者我应该只使用构造函数"在粗体部分中;因为让我问的是我想知道它是否是保证行为 - 我们都可以同意,与显式构造函数相比,可读代码更好。
不是动态分配使您的 struct
成员零命名;这是您的语法:
X* ptr = new X();
// ^^
//
// as opposed to just:
X* ptr = new X;
如果您要保证它,请继续写下来。:)
一种与自动存储 - 持续等效物相吻合的替代方案是使用较新的{}
语法:
X* ptr = new X{}; // dynamic
X obj{}; // automatic
和带有静态存储持续时间的对象始终是Zero Initialist的,无论如何您默认情况下您都在那里覆盖。
如果要给班级的特定值,请始终使用构造函数。从字面上看,构造函数的目的。您唯一不需要编写设置所需值的构造函数的时间是,如果语言为您提供了一个像复制构造函数为您的构造函数。默认的构造函数不在此列表上的int
和其他类型的类型上,因此您必须将构造函数添加到自己的类型中,以适当地设置它们。
只要您没有任何构造函数,所有成员都是公共的,并且不涉及继承,您的结构/类可能是汇总的。
要获取便携式零限制,只需使用执行零Intialization的X x = {};
。
这是有关聚合的标准报价(8.5.1):
汇总是不提供用户的数组或类(第9条)(第9条) 构造函数(12.1),没有用于非静态的撑杆或平等限制器 数据成员(9.2),没有私人或受保护的非静态数据成员 (第11条),没有基类(第10条),没有虚拟功能 (10.3)。
参考:为什么我不能支撑从另一个结构派生的结构?
- 多成员Constexpr结构初始化
- 为什么用结构初始化数组需要指定结构名称
- 使用指定的初始值设定项聚合匿名结构初始化
- 不同的类或结构初始化方法之间的性能差异是什么?
- 如何在结构初始化中获取成员C++
- C++正确的结构初始化
- 使用大括号进行结构初始化
- 内部结构初始化不起作用 - C++
- 使用嵌套结构初始化并集
- 使用匿名结构初始化联合
- 结构初始化语法
- 结构初始化的 C++ 向量
- C++嵌套结构初始化和访问成员
- 结构初始化中的常量正确性
- 使用 C++ 中的自定义元素进行 Const 结构初始化
- 如何在结构C++初始化内置数组
- Visual C++ 模板类成员结构初始化语法糖
- C++结构初始化
- C 在结构初始化过程中带有内部阵列的奇怪错误
- 此C/C 的结构初始化器如何使用足够的字段工作