为什么堆分配数组的大小需要初始化器-列表初始化
Why is the size of a heap-allocated array required with initializer-list initialization?
虽然我可以写
int n[] {1, 2, 3};
我不能写
int *m = new int[] {1, 2, 3};
应该是
int *m = new int[3] {1, 2, 3};
这是什么原因?
请记住,new在c++中实际上是一个操作符。
这是因为new操作符的定义方式;也就是说,它需要请求内存的大小作为一个明确的输入参数。因此,它不能通过初始化列表成员的计数来推导。
要理解这一点,您需要了解new操作符是如何工作的。New返回一个指向新分配的内存块开始的指针。所以当我们输入
int* p = new int;
分配的内存只包含一个元素。但是当我们输入
int* foo = new [3];
为int类型的元素分配了一块内存,其中"3"是整型元素的内存块号。这告诉编译器为3个整数分配内存。当我们这样做
int* p = new int[3]{1,2,3}
我们要求编译器分配3个存储整型值的内存位置。与此同时,我们也为这些内存位置赋值。
现在如果我们这样做
int* p = new int[] {1,2,3}
我们没有告诉编译器要分配多少内存,但同时我们试图分配3个内存位置,但我们没有分配那么多内存。在这种情况下,编译器只分配1块内存。第一个值被赋值。这将导致运行时错误。
现在奇怪的是,如果下面是允许的,并且编译器足够智能地分配3个值
int n[] = {1, 2, 3}
为什么不呢
int *p = new int [] {1,2,3}
我认为这是问题所在,因为新操作符是如何设计的。你可以尝试重载new操作符来解决这个问题。
希望对你有帮助。
编辑:我尝试了一些虚拟代码VS.似乎如果你这样做
int* p = new int [] {1,2,3}
这是一个崩溃。但是当你这样做
int* p = new int []{1}
这完全没问题。这证明编译器将其解释为仅分配1块内存的命令。
相关文章:
- C++类 - 初始化列表 - 递归 - 按值传递
- 在初始化列表之外手动调用基类的构造函数
- C++:带有大括号初始化列表的函数调用表达式 - 标准是否规定在单个元素列表的微不足道的情况下忽略大括号?
- std::map与谓词与初始化列表
- 类内初始化与构造函数初始化列表的顺序
- 当返回语句时,逗号运算符、大括号初始化列表和 std::unique_ptr 组合在一起
- 使用初始化列表填充C++中的多维结构数组时出现问题
- 如何在初始化列表中的构造函数之后初始化变量/对象?
- C++初始化列表与分配值
- C++初始化列表中的向量集大小或调整大小
- 在构造函数初始化列表中使用 std::variant
- emplace_back初始化列表错误,当初始化列表在独立变量上工作时
- 解释了构造函数成员初始化列表
- 使用初始化列表时如何获取私有数据?
- 用初始化列表和超类构造函数声明子类构造函数的正确方式
- 如何在成员初始化列表中声明共享指针
- 庞大的初始化列表,如何修复"fatal error C1060: compiler is out of heap space"
- 我可以检查初始化列表中设置的构造函数主体中的变量吗
- 使用整数初始化列表初始化长双精度的向量
- 是否可以在C++中使用初始化列表设置数组的特定成员?