首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C++数据成员对齐和数组打包

C++数据成员对齐和数组打包
EN

Stack Overflow用户
提问于 2009-11-05 04:24:08
回答 8查看 10.4K关注 0票数 17

在代码审查期间,我遇到了一些代码,它们定义了如下的简单结构:

代码语言:javascript
复制
class foo {
   unsigned char a;
   unsigned char b;
   unsigned char c;
}

在其他地方,定义了这些对象的数组:

代码语言:javascript
复制
foo listOfFoos[SOME_NUM];

随后,这些结构被原始复制到一个缓冲区中:

代码语言:javascript
复制
memcpy(pBuff,listOfFoos,3*SOME_NUM);

此代码依赖于以下假设: a.)foo的大小为3,不应用填充,b)这些对象的数组被打包,它们之间没有填充。

我在两个平台(RedHat 64b,Solaris9)上用GNU尝试过它,它在这两个平台上都能工作。

上述假设有效吗?如果不是,在什么情况下(例如,操作系统/编译器中的更改)可能会失败?

EN

回答 8

Stack Overflow用户

回答已采纳

发布于 2009-11-05 04:30:54

对象的数组需要是连续的,所以对象之间永远不会有填充,尽管填充可以添加到对象的末尾(产生几乎相同的效果)。

考虑到您正在使用char,这些假设可能通常是正确的,但是C++标准肯定不能保证这一点。不同的编译器,甚至只是传递给当前编译器的标志的更改,都可能导致在结构的元素之间插入填充,或者在结构的最后一个元素之后插入填充,或者两者都插入。

票数 20
EN

Stack Overflow用户

发布于 2009-11-05 04:29:19

这样做肯定会更安全:

代码语言:javascript
复制
sizeof(foo) * SOME_NUM
票数 22
EN

Stack Overflow用户

发布于 2009-11-05 04:40:23

如果像这样复制数组,应该使用

代码语言:javascript
复制
memcpy(pBuff,listOfFoos,sizeof(listOfFoos));

只要您将pBuff分配到相同的大小,这将始终起作用。通过这种方式,您根本不需要对填充和对齐进行任何假设。

大多数编译器将结构或类与所包含的最大类型的所需对齐方式对齐。在字符的情况下,这意味着没有对齐和填充,但如果添加一个短字符,例如,您的类将是6个字节大小,并在最后一个字符和短字符之间添加一个字节的填充。

票数 6
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1676385

复制
相关文章

相似问题

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