了解C ++结构大小

时间:2011-01-09 16:48:06

标签: c++ struct sizeof

请考虑以下代码:

struct CExample  {
    int a; 
}            

int main(int argc, char* argv[]) {  

    CExample ce1;  
    CExample ce2;  

    cout << "Size:" << sizeof(ce1) << " Address: " << &ce1 << endl;   
    cout << "Size:" << sizeof(ce2) << " Address: " << &ce2 << endl;   

    CExample ceArr[2];
    cout << "Size:" << sizeof(ceArr[0])<< " Address: "<< &ceArr[0] <<endl;
    cout << "Size:" << sizeof(ceArr[1])<< " Address: "<< &ceArr[1] <<endl;

    return 0;
}

输出示例:
ce1:尺寸= 4,地址:0039FAA0
ce2:尺寸= 4,地址:0039FA94
ceArr [0]:大小= 4,地址:0039FA84
ceArr [1]:大小= 4,地址:0039FA88

使用代码,前两个对象(ce1和ce2)的地址之间有一个12字节,但是数组中的对象之间只有4个字节的差异。

我认为数据对齐会与问题有关,但我仍然感到难过。知道这里到底发生了什么吗?

4 个答案:

答案 0 :(得分:15)

因为数组中的对象必须是连续的。在堆栈上连续声明的对象(在源代码中,而不是机器上)不是[必须是连续的],尽管它们可以是。

答案 1 :(得分:6)

标准对此没有任何说明。编译器可以自由地在项目之间插入它想要的任何填充。

(如果我不得不猜测,我猜你的编译器在调试模式下实现某种形式的堆栈保护/ canary(并且你在调试模式下编译))

答案 2 :(得分:1)

编译器不仅使用堆栈来保存局部变量 - 它还将它用于参数传递,以及由std::cout引起的一些开销。这可能是变量之间的额外空间用于。

如果您改为制作变量static,请执行以下操作:

static CExample ce;
static CExample ce2;

static CExample ceArr[2];

...变量将被放置在BSS内存中,并且对齐更可能是您期望的。

其他答案澄清了数组打包和个别项目的原因......

答案 3 :(得分:0)

原因是,在大多数体系结构中,未对齐的负载很慢。有关详细解释,请参阅data structure alignment上的维基百科条目。编译器将每个数据结构放在数据字的开头。但是,在数组中,项目是连续放置在内存中的(如C ++标准所要求的那样)。