结构的大小会受到数组元数据的影响吗?
Can sizeof of struct be affected by array metadata?
关于struct
的sizeof
(不)等于其元素sizeof
之和,已经存在许多问题。通常这是由于数据对齐。这个问题与数据对齐无关,因此请假设所有类型的大小都是对齐的倍数(例如 4B)。
如此处所述,分配数组将导致存储一些元数据,其大小与分配的数组大小相当。假设我们有以下代码:
const int size = 10;
struct X {
int someInt;
int array[size];
};
struct Y {
int someInt;
T array[size];
};
由于size
在编译时是已知的,因此编译器应该足够聪明,以确定在X
的情况下不需要存储任何元数据。即使在Y
的情况下,编译器也可以足够聪明地遵循这种推理(这里可能存在 C 和 C++ 之间的差异,因为C++中还有为T
的单个实例调用析构函数的额外要求)。
我的问题是:我能保证sizeof(X) == (size + 1) * sizeof(int)
还是特定于编译器?或者更一般地说,是sizeof(Y) == size * sizeof(T) + sizeof(int)
?
编辑:希望澄清一点:问题是关于C和C++的。问这个问题的最初动机也是这样的。如果我跑
X *foo = new X[100];
或者它在代码中的某个地方是 C 等效的,它会创建一个大小为100 * (size + 1) * sizeof(int)
的连续内存块吗?
常见实现中的 C 数组不会在其周围存储任何元数据,但是,可以将填充添加到结构中,以便a_struct_ptr + 1
有足够的对齐方式进行a_struct
。
在第一个结构({ int someInt; int array[size]; }
)的情况下,不需要填充,所以
sizeof(X) == (size + 1) * sizeof(int)
应该成立(虽然,我认为编译器没有义务保证它)。
对于第二个结构,T
和int
的对齐要求可能会导致向结构中添加填充,从而使公式无效。
元数据可以隐藏在struct
成员之间。 我从未见过元数据的这种用途,但编译器可以在一定程度上使用类型的对齐方式,通过强制int
的对齐大于 4 个字节等int
宽度,在两个int
成员之间提供不连续的内存。 如果编译器将其用于元数据、性能填充或恶意,则无关紧要。 关键是它可能存在。
C99/C11 提供max_align_t
,因此类型本身不会超过根据 C 规范的对齐方式。
小于或等于实现在所有上下文中支持的最大对齐的对齐表示,该对齐等于
_Alignof (max_align_t)
。 §6.2.811dr §6.2.8 2
max_align_t
这是一种对象类型,其对齐方式与所有上下文中的实现所支持的对齐方式一样大; §7.19 2
因此,任何小于max_align_t
的结构成员都会在潜在上下文中受到填充/元数据的影响。
- 在C++中打印指向不同基元数据类型的指针的内存地址
- 以非特权用户身份查询 NTFS 特殊文件的元数据?
- 如何使用 Google Test 向测试添加元数据 / 如何将数据从 Google Test 发送到 TestEven
- 将复杂的非基元C++数据类型转换为 Erlang/Elixir 格式,以使用 NIF 导出方法
- 从模板创建通用打印函数,以打印基元数据类型变量的值
- 在 C++ 中修改 Grpc 双向流式处理期间的元数据
- cpp / c ++中的grpc客户端代码,元数据x-api-key/x-goog-api-key不起作用,给了我语音A
- 如何使用gRPC在客户端和服务器之间双向发送和接收流元数据
- 即使基类和派生类只使用基元数据类型,我是否需要定义虚拟析构函数
- 如何处理错误"E1696命令行错误:无法在Visual Studio 2017中打开元数据文件"mscorlib.dll"?
- 元数据操作失败LNK2022错误 (8013118D):重复类型中的布局信息不一致 (选择设备参数):(0x020002
- C++11 标准中的哪一部分规定了基元数据类型大小之间的相对顺序?
- 使用 ffmpeg 添加元数据信息
- WIC - Exif 元数据查询 - 如何获取图像说明
- 从Qt应用程序读取元数据
- 如何将编译时元数据/行为添加到特定函数
- 从编码域中的 MPEG 文件中读取元数据
- 在C 中显示图像及其元数据
- 如何用libcurl定义元数据
- 结构的大小会受到数组元数据的影响吗?