You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言用_Alignas指定对齐后为何出现内存填充?

关于C语言内存对齐与_Alignas的疑问解答

让我一步步帮你理清这两个困惑点:

1. 为什么cz后面会出现内存填充?

首先要明确栈内存的增长方向:大部分系统中,栈是从高地址向低地址分配内存的。你代码里变量的声明顺序是dx→ca→cx→dz→cb→cz,但实际在栈中的地址顺序是反过来的:dx(最高地址)→ca→cx→dz→cb→cz(最低地址)。

你看到的“cz后面的填充”,其实是在cb和cz之间的空间——因为_Alignas(double)要求cz的地址必须是8字节的倍数(double类型的对齐要求)。而cb的地址是0x28ff0f,它的下一个可用地址(0x28ff10)并不满足8字节对齐,所以编译器必须在cb和cz之间插入填充字节,把cz“推”到符合对齐要求的地址(0x28ff08,这是离0x28ff10最近的、更低的8字节对齐地址)。

2. 为什么填充是6字节,而不是7字节?

这里要区分两个概念:对齐要求和变量大小。_Alignas(double)只是要求cz的地址是8字节的倍数,并没有改变cz本身的大小(它还是1字节的unsigned char)。

我们来算一下:

  • cb的地址是0x28ff0f,它占用1字节,所以下一个未使用的地址是0x28ff10。
  • 我们需要找到比0x28ff10小的最大的8字节对齐地址:0x28ff08(因为0x28ff08 % 8 = 0)。
  • 从0x28ff08到0x28ff0f之间共有7个地址:0x28ff08(cz本身) + 6个填充地址(0x28ff09到0x28ff0e),正好到0x28ff0f(cb的地址)。

如果填充7字节的话,cz的地址会变成0x28ff07,这个地址不是8的倍数(0x28ff07 %8 =7),不符合_Alignas(double)的要求,所以编译器不会这么做。

总结一下:_Alignas的作用是保证变量的起始地址符合指定的对齐边界,为了满足这个要求,编译器会在栈上的变量之间插入必要的填充字节,填充的数量由目标地址的对齐要求和前一个变量的位置决定。

内容的提问来源于stack exchange,提问作者AlexQualcosa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 06:37:03