请考虑以下类型:
  struct A {};
  struct B : A { int i; };标准要求的sizeof(A) > 0。
由于空基优化,sizeof(B)应为4。然而,在GCC 4.1.1上是5(我在这方面使用的是1包)。而且不一致-我的一些文件得到了它,一些没有。还不能确定有什么不同,我们有一个很大的问题。
在我使用的其他三个编译器(微软和飞思卡尔)上,我没有这个问题。根据this article的说法,空基优化显然是可选的。
在GCC 4.1.1中有没有编译器选项或编译指示来调优这一点?我可以解决这个问题,但我想先了解发生了什么。我用谷歌搜索了一段时间,似乎什么也找不到。
发布于 2009-02-13 19:57:36
这总是会发生的。在我弄清楚之前,我会立即发帖。也许张贴的行为让我以一种不同的方式思考。
因此,在我的问题中,示例有点过于简单。实际上更像是这样:
struct Base {};
struct C1 : Base { int i; }
struct C2 : Base { C1 c; int i; }sizeof(C1)在所有平台上都是正确的4,但是sizeof(C2)在GCC上是9而不是8。还有..。很明显,根据我在原问题中链接的文章的最后一点,唯一正确的事情就是GCC。我将在这里引用它(来自Nathan Meyer):
根据编译器必须遵守的ABI规范,可以进行一整套相关的“空子对象”优化。(几年前,杰森·梅里尔向我指出了其中一些问题。)例如,考虑三个(空)类型A、B和C的结构成员,以及第四个非空成员。顺理成章地,它们都可以占用相同的地址,只要它们彼此之间或与包含类没有任何共同的基础。在实践中,一个常见的陷阱是让类的第一个(或唯一)成员派生自与类相同的空基。编译器必须插入填充,以便这两个子对象具有不同的地址。这实际上发生在具有interator成员的迭代器适配器中,这两个成员都派生自std::iterator。一个不小心实现的标准std::reverse_iterator可能会出现这个问题。
所以,我看到的不一致只发生在我有上述模式的情况下。我从一个空结构派生的其他地方都没问题。
工作起来很容易。感谢大家的评论和回答。
发布于 2009-05-28 07:53:42
使用标准填充时,GCC C++遵循以下规则:
注:__attribute__((__packed__))或更改默认装箱将修改这些规则。
MSVC++遵循以下规则:
注:#pragma pack或更改默认装箱将修改这些规则。
发布于 2009-02-13 19:44:37
这并不是一个完整的答案,但是GCC Manual提到g++有时会将空的基类放在错误的偏移量上。请参阅关于-Wabi选项的部分。
https://stackoverflow.com/questions/547290
复制相似问题