结构体占用内存大小

1、总结:

结构体大小的计算:
1. 结构体中成员变量的大小对齐
2. 结构体的总大小为各成员变量大小的总和,加上结构体头的大小
3. 结构体头的大小由编译器决定,一般为1或2个字节,但也可能是4或8个字节
4. 结构体中各成员变量的大小由编译器决定,一般为1、2、4、8个字节,但也可能是16、32、64个字节
5. 结构体中各成员变量的大小对齐,以结构体中最大的成员变量大小为基准
​
关键点	​说明
​成员对齐	每个成员的起始地址必须是其类型大小的整数倍。
​整体对齐	结构体总大小必须是最大成员对齐值的整数倍。
​填充字节	编译器自动插入不可见的填充字节以满足对齐规则。
​优化手段	调整成员顺序、使用 #pragma pack 或 alignas、显式填充。
​注意事项	强制修改对齐可能导致性能下降或平台兼容性问题,慎用 #pragma pack(1)。

公式:
结构体大小 = Σ(成员大小 + 填充字节) + 末尾填充(若需要)
填充字节 = (对齐值 - (当前偏移 % 对齐值)) % 对齐值

基本数据类型占用内存大小(平台差异,可用sizeof()确定变量占用内存的大小):
数据类型	典型大小(字节)	对齐值(字节)
char	1	1
short	2	2
int	4	4
float	4	4
double	8	8
指针(32位)	4	4
指针(64位)	8	8

2、举例:

#include <stdalign.h>
#include <stdio.h>

// 示例结构体
typedef struct {
    char a;      // 1 字节
    int b;       // 4 字节
    double c;    // 8 字节
} MyStruct;

int main() {
    /*
    计算过程:
    char a 占 1 字节。
    int b 需要起始地址为 4 的倍数,因此在 a 后填充 3 字节。
    int b 占 4 字节。
    double c 起始地址为 8(已对齐),占 8 字节。
    总大小 = 1 + 3(填充) + 4 + 8 = 16 字节。
    结构体整体需要对齐到 double 的大小(8 字节),16 是 8 的整数倍,无需额外填充。
    */
    printf("结构体大小:%zu 字节\n", sizeof(MyStruct));  // 输出:16 字节(对齐后的结果)


    // 修改对齐方式
    // 1、#pragma pack(1)  // 强制 1 字节对齐
    #pragma pack(1)     // 1 字节对齐(无填充)
    struct Packed {
        char a;    // 1
        int b;     // 4
        double c;  // 8
    };             // 总大小 = 1 + 4 + 8 = 13
    printf("结构体大小:%zu 字节\n", sizeof(struct Packed));  // 输出:13 字节(无填充)
    #pragma pack()  // 恢复默认对齐
    /* 2. 使用 alignas 关键字(C11 / C++11)
    需要使用MSVC扩展语法,在结构体定义前加上 __declspec(align(...)),否则会报错 
    C++不需要添加stdalign.h头文件   
    */
    

    struct Aligned {
        char a;
        __declspec(align(8)) int b;  // 强制 b 对齐到 8 字节
        double c;
    };  // 总大小 = 1 + 7(填充) + 4 + 0 + 8 = 20(需对齐到 8 的倍数 → 24)
    printf("结构体大小:%zu 字节\n", sizeof(struct Aligned));  // 输出:24 字节(对齐后的结果)

    return 0;
}

扩展:控制内存对齐alignas、_Alignas、#pragma pack(1)、__declspec(align(8))区别:

关键区别总结
对比项alignas/_Alignas#pragma pack(n)__declspec(align(n))
标准支持C11/C++11 标准非标准(编译器扩展)非标准(MSVC 扩展)
跨平台性✔️(GCC/Clang/MSVC)✔️(所有编译器支持类似语法)❌(仅 MSVC)
作用目标变量、类型、结构体成员结构体/联合体整体对齐变量、类型、结构体成员
对齐值要求2 的幂次,且 ≥ 自然对齐值任意正整数(通常 1/2/4/8/16)2 的幂次,且 ≥ 自然对齐值
典型场景SIMD 指令、硬件寄存器映射网络协议、文件格式解析Windows 高性能计算
内存布局影响精确控制对齐,可能增加填充减少填充,可能导致未对齐访问精确控制对齐,可能增加填充

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值