为什么不能用两层列表初始化器来初始化 2D std::array?

2023-12-21

有人可以帮助我理解为什么我的编译器不能/不能推断出这一点吗? (使用 g++ 7.3)

不起作用:

#include <array>
std::array<std::array<double,2>,2> f() {
 return {{0,0},{0,0}};
}

工作正常:

#include <array>
std::array<std::array<double,2>,2> f() {
 return {std::array<double,2>{0,0},{0,0}};
}

奇怪的是,这也失败了:

#include <array>
std::array<std::array<double,2>,2> f() {
 return std::array<std::array<double,2>,2>{{0,0},{0,0}};
}

@1201ProgramAlarm 指出添加另一组花括号是有效的:

#include <array>
std::array<std::array<double,2>,2> f() {
 return {{{0,0},{0,0}}};
}

它使用聚合初始化,因为std::array没有大括号初始化列表的构造函数。很好,但是为什么/它是如何工作的呢?

std::array<double,2> x{1,2};

为什么它处理这种情况而不处理嵌套情况?


容器std::array等效地是一个包含 C 数组的结构(实现可能未实现std::array这样,但要保证语义相同),所以应该用两层大括号初始化,即

#include <array>
std::array<std::array<double,2>,2> f() {
   return {{{{0,0}},{{0,0}}}};
} 

当然,初始化列表中的大括号可以像我们通常对二维数组所做的那样省略:

int arr[2][2] = {0,1,2,3};

...但是在省略之前以省略的大括号开头的初始值设定项列表不应在省略之后以左大括号开头。换句话说,如果初始值设定项列表以左大括号开头,则编译器将不会考虑该初始值设定项列表已省略最外层大括号的可能性。

在你的初始化程序中{{0,0},{0,0}}, 子初始化器{0,0},{0,0}以左大括号开头,因此它用于初始化 C 数组本身。然而,列表中有两个子句,而只有一个 C 数组,则会出现错误。

在你的初始化程序中{std::array<double,2>{0,0},{0,0}}, 子初始化器std::array<double,2>{0,0},{0,0}不以左大括号开头,因此可以用来初始化 C 数组的元素,这是可以的(递归地,{0,0}可以初始化一个std::array<double,2>因为子初始化器0,0不以左大括号开头)。


一个建议:使用大括号的省略规则,您可以省略所有内部大括号,就像我们通常对二维数组所做的那样:

#include <array>
std::array<std::array<double,2>,2> f() {
   return {0,0,0,0};
} 
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

为什么不能用两层列表初始化器来初始化 2D std::array? 的相关文章

  • 在 C# 中转换 VbScript 函数(Right、Len、IsNumeric、CInt)

    同样 我在 VbScript 中得到了以下代码 您能建议一下 C 中的等效代码吗 Function GetNavID Title getNavID UCase Left Title InStr Title 1 End Function 我已
  • 了解 VerQueryValue

    在 MSDN 上 我注意到 VerQueryValue 函数的以下内容 lplp缓冲区 输出 低电压空洞当此方法返回时 包含指向 pBlock 指向的缓冲区中所请求版本信息的指针的地址 当关联的 pBlock 内存被释放时 lplpBuff
  • 确保 unsigned int/long 始终在 C# 中的检查上下文中执行

    有没有人觉得奇怪 uint 和 ulong 的默认上下文是未检查的 而不是检查的 因为它们旨在表示永远不能为负的值 因此 如果某些代码试图违反该约束 在我看来 自然且首选的行为是抛出异常 而不是返回最大值 这很容易使重要数据处于无效状态并且
  • 如何在方法模板中使用模板类型的引用传递参数?

    我目前正在努力编译以下代码 首先是包含带有方法模板的类的头文件 ConfigurationContext h class ConfigurationContext public template
  • MouseDoubleClick 事件不会冒泡

    我的场景经过简化 我有一个包含员工行的 ListView 在每个员工行中 都有 增加 和 减少 按钮来调整他的工资 假设在我的程序中 双击 员工 行意味着 解雇此人 The problem是当我快速单击 增加 时 这会触发 ListView
  • DataGridView小数不排序

    好吧 我有一个 DataGridView 它的数据绑定如下 dataGridViewChartOre AutoGenerateColumns false dataGridViewChartOre DataSource xml GetOreC
  • gcc 删除内联汇编代码

    看起来 gcc 4 6 2 删除了它认为函数中未使用的代码 test c int main void goto exit handler asm volatile jmp 0x0 exit return 0 拆解main 0x0804840
  • 获取进程的所有 DLL

    我想获取为给定进程加载的所有 dll 的列表 我目前正在使用 NET框架4 0 我知道有一个bug https connect microsoft com VisualStudio feedback details 546430 syste
  • 使用 c# 中的 c++ ref 中的引用从 C# 调用 C++ 代码错误

    所以在我的 c dll 文件中我得到了以下函数 DLL void GetUserPass char userName char passWord userName ceva passWord altceva 现在我想从 c 调用它 但它给了
  • 使用 OpenSSL 库在 C++ 中生成 SHA 哈希值

    如何使用以下命令生成 SHA1 或 SHA2 哈希值OpenSSL https openssl org图书馆 我搜索了谷歌 找不到任何函数或示例代码 从命令行来看 很简单 printf compute sha1 openssl sha1 您
  • 为什么这段代码不会产生编译错误?

    template
  • 如何在控制台程序中获取鼠标位置?

    如何在 Windows 控制台程序中用 C 获取鼠标单击位置 点击时返回鼠标位置的变量 我想用简单的文本命令绘制一个菜单 这样当有人点击时 游戏就会注册它并知道位置 我知道如何做我需要做的一切 除了单击时获取鼠标位置 您需要使用 Conso
  • 初始化二维数组时出现分段错误

    我已经检查过我的代码是否正确地划分了内存空间 但是一旦我尝试将 2D 数组初始化为某些值 然后对这些值求和 我就会在 2x2 数组上收到分段错误 我想最终将我的代码扩展到更大的数组 但我什至无法让它在这里工作 我知道有很多关于 malloc
  • 比较 C# 中的对象属性[关闭]

    Closed 这个问题是基于意见的 help closed questions 目前不接受答案 Locked 这个问题及其答案是locked help locked posts因为这个问题是题外话 但却具有历史意义 目前不接受新的答案或互动
  • 如何正确对齐 WPF GeometryGroup 中的路径?

    我正在使用一个GeometryGroup在圆的中心绘制一个符号 下面的示例显示了我在对此进行实验时的尝试之一 它具有从同一原点 32 32 出发的三条直线
  • 如何重写(重新实现)QFileSystemModel 中的成员函数

    我已经为此苦苦挣扎了一段时间 Qt s QFileSystemModel由于图标获取算法非常糟糕 在获取数百个文件时速度非常慢 我想完全禁用图标 它们被提取到QFileSystemModel data方法不是虚拟的 QFileSystemM
  • 有没有办法将复选框列表绑定到 asp.net mvc 中的模型

    我在这里寻找一种快速简便的方法来在模型中发生回发时绑定复选框列表项的列表 显然现在常见的做法似乎是这样的form GetValues checkboxList 0 Contains true 这看起来很痛苦而且不太安全 有没有一种方法可以绑
  • Opencv 对象检测:ORB GPU 检测器和 SURF GPU 描述符提取器

    我只是做了一个小实验来尝试不同的检测器 描述符组合 我的代码使用 ORB GPU 检测器来检测特征 并使用 SURF GPU 描述符来计算描述符 我使用 BruteForceMatcher GPU 来匹配描述符 并使用 knnMatch 方
  • 如何将 IDispatch* 放入托管代码中

    我一直在考虑尝试使用 C 编写一个实现 OPOS 服务对象的 COM 对象 我已经使用自动化和 MFC 在 C 中完成了它 这并不太困难 所以我坚持尝试将其转换为一种方法 我将排除界面中的其他方法 因为它们很简单 或者我希望如此 id 6
  • Image.Save 异常“GDI+ 中发生一般错误。”保存到 MemoryStream 时

    我有一个服务器客户端应用程序 我想从服务器获取屏幕截图 但在线bitmap Save ms System Drawing Imaging ImageFormat Png 我得到这个例外 A generic error occurred in

随机推荐