首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么结构大小随结构中的枚举位域而变化(标准C)

为什么结构大小随结构中的枚举位域而变化(标准C)
EN

Stack Overflow用户
提问于 2022-07-20 07:40:55
回答 1查看 100关注 0票数 3

在使用这个问题中的代码时,我发现当使用8位宽枚举而不是uint8_t类型时,结构的大小会增加。

请参阅以下代码示例:

代码选项A

代码语言:javascript
复制
typedef enum { A, B, C, MAX = 0xFF } my_enum;

struct my_compact_struct_option_a
{
    my_enum field1 : 8; // limiting enum size to 8 bits 
    uint8_t second_element[6];
    uint16_t third_element;
};

此结构second_element中的第二个变量的偏移量为1。这表明枚举field1仅限于uint8_t大小,但是结构的大小为12字节。这对我来说是意外的。

把这个和

代码选项B

代码语言:javascript
复制
typedef uint8_t my_type;

struct my_compact_struct_option_b
{
    my_type field1; 
    uint8_t second_element[6];
    uint16_t third_element;
};

在这里,second_element的偏移量也是1,但是这个结构的大小是10字节。这是意料之中的。

为什么第一个代码示例中的结构增加到12个字节?

你总是可以自己试试这段代码的。

EN

回答 1

Stack Overflow用户

发布于 2022-07-25 16:52:56

正如在另一个答案中提到的,C标准指出,实现可以使用任何足够大的存储单元来容纳位字段。由于默认情况下,enum实际上是int,所以大多数编译器都会为位字段使用int大小的存储单元。特别是,gcc和MSVC都将创建一个4字节的enum和一个12字节的struct

在评论中具体说明的情况下:

代码语言:javascript
复制
 struct foo { int a : 8; char b; };

gcc和clang给它的大小为4,而MSVC给它的大小为8。

因此,似乎正在发生的是,a驻留在一个int大小的存储单元中,因为这是位字段的基本类型。结构的对齐是4,因为这是最大字段的大小,特别是容纳位字段的int大小单元。

gcc和clang似乎与MSVC不同之处在于,gcc和clang将允许非位字段占用与位字段相同的存储单元,而MSVC则将比特字段保留在它们自己的存储单元中。

如果您想使enum类型更小,有一些实现的特定方法。

在gcc中,use可以使用packed属性:

代码语言:javascript
复制
typedef enum __attribute__((__packed__)) { A, B, C, MAX = 0xFF } my_enum;

也可以传递-fshort-enums标志以缩小所有枚举的大小。这两种方法都会导致my_enum大小为1字节,struct my_compact_struct_option_a为10字节。

clang允许您使用以下语法指定枚举的大小:

代码语言:javascript
复制
typedef enum : char { A, B, C, MAX = 0xFF } my_enum;
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/73047713

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档