【问题标题】:C++ Bitfield Struct size definition (Why is it packed larger?)C++ Bitfield Struct 大小定义(为什么打包得更大?)
【发布时间】:2014-07-08 18:44:40
【问题描述】:

我有一个关于 C++ 中的位打包的问题。

假设我们有一个用 C++ 定义的结构。如下:

typedef struct
{
    unsigned long byte_half : 4;             //0.5
    unsigned long byte_oneAndHalf : 12;      //2
    union
    {
        unsigned long byte_union_one_1 : 8;  //3
        unsigned long byte_union_one_2 : 8;  //3
        unsigned long byte_union_one_3 : 8;  //3
    };
    unsigned long byte_one        : 8;       //4
}LongStruct;

这是一个名为 LongStruct 的结构。从外观上看,它占用了 4 个字节,并且可以放入一个 long 中。现在我执行以下行:

int size = sizeof(LongStruct);

我看了一下大小,期望它的值是 4。结果我得到了 12。我以什么方式错误地可视化了我的结构?

提前感谢您能给我的任何帮助。

【问题讨论】:

  • long 更改为char(或short 用于12 位字段)。
  • 看在上帝的份上,不要使用邪恶的typedef struct {..} name;建设
  • 我建议去掉 C# 部分。如果你想得到答案,请发布另一个问题。

标签: c++ struct unions bit-fields


【解决方案1】:

union 扩展为long,所以它的大小是 4 个字节而不是 1 个字节。

因此,它与结构开头的 4 字节偏移对齐。

此外,整个结构被扩展为4字节的倍数。

所以实际的结构是这样的:

unsigned long byte_half       :  4; // bits  0 -  3
unsigned long byte_oneAndHalf : 12; // bits  4 - 15
unsigned long byte_padding_1  : 16; // bits 16 - 31 // align union

union
{
    unsigned long byte_union_one_1 :  8; // bits 32 - 39
    unsigned long byte_union_one_2 :  8; // bits 32 - 39
    unsigned long byte_union_one_3 :  8; // bits 32 - 39
    unsigned long byte_padding_2   : 24; // bits 40 - 63 // expand union
};

unsigned long byte_one       :  8; // bits 64 - 71
unsigned long byte_padding_3 : 24; // bits 72 - 95 // expand structure

因此总大小为 96 位(12 字节)。

【讨论】:

  • 感谢您非常详细的回答!
【解决方案2】:

匿名联合并没有替换它的属性,而是在你的位域结构中间占用一个四字节的块。所以你的前两个成员是两个字节+两个填充。那么你的联合是一个字节加三个填充。然后你的最后一个成员是一个字节和三个填充。总数是您观察到的 12 个。

我将尝试深入研究该标准,以确切了解它对匿名联合位域的描述。或者,如果您描述您要解决的真正问题,我们也可以考虑回答。

顺便说一句,你有这个标记的 C++ 所以强烈喜欢struct X {}; 而不是typedef struct {} X;

【讨论】:

  • 如果没有记错的话,标准对位域的承诺很少。这可能有助于您的搜索。
  • 感谢您的回答!是的,我会改变这个定义,我正在遵循一些遗留代码,但它可能不值得保留这种表示法。
猜你喜欢
  • 2011-01-25
  • 2018-08-04
  • 2013-01-19
  • 1970-01-01
  • 1970-01-01
  • 2018-05-19
  • 2011-02-24
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多