MST

星途 面试题库

面试题:C语言结构体与联合体嵌套设计及内存对齐

设计一个复杂的数据结构,结构体中嵌套联合体,联合体中再嵌套结构体,并且每个子结构体都有不同的数据类型。要求考虑内存对齐问题,写出完整的C语言代码,并分析最终的数据结构占用的内存大小以及内存布局是如何形成的。
41.2万 热度难度
编程语言C

知识考点

AI 面试

面试题答案

一键面试
#include <stdio.h>
#include <stdint.h>

// 定义第一个子结构体
typedef struct {
    int8_t a;
    int16_t b;
} SubStruct1;

// 定义第二个子结构体
typedef struct {
    int32_t c;
    double d;
} SubStruct2;

// 定义联合体
typedef union {
    SubStruct1 sub1;
    SubStruct2 sub2;
} MyUnion;

// 定义主结构体
typedef struct {
    char e;
    MyUnion u;
    float f;
} MyStruct;

int main() {
    printf("Size of SubStruct1: %zu bytes\n", sizeof(SubStruct1));
    printf("Size of SubStruct2: %zu bytes\n", sizeof(SubStruct2));
    printf("Size of MyUnion: %zu bytes\n", sizeof(MyUnion));
    printf("Size of MyStruct: %zu bytes\n", sizeof(MyStruct));

    return 0;
}

内存大小分析

  1. SubStruct1
    • int8_t a 占1个字节。
    • int16_t b 占2个字节。
    • 由于内存对齐,int8_t 之后需要填充1个字节,以满足 int16_t 的对齐要求(int16_t 要求2字节对齐),所以 SubStruct1 总共占用4个字节。
  2. SubStruct2
    • int32_t c 占4个字节。
    • double d 占8个字节。
    • int32_t 之后需要填充4个字节,以满足 double 的对齐要求(double 要求8字节对齐),所以 SubStruct2 总共占用16个字节。
  3. MyUnion
    • 联合体的大小是其最大成员的大小,所以 MyUnion 占用16个字节。
  4. MyStruct
    • char e 占1个字节。
    • MyUnion u 占16个字节。
    • float f 占4个字节。
    • char e 之后需要填充3个字节,以满足 MyUnion 的对齐要求(MyUnion 要求16字节对齐)。MyUnion 之后需要填充4个字节,以满足 float f 的对齐要求(float 要求4字节对齐)。所以 MyStruct 总共占用1 + 3 + 16 + 4 = 24 个字节。

内存布局

  1. MyStruct
    • 先存储 char e,然后填充3个字节。
    • 接着存储 MyUnion,由于 MyUnion 内部是联合体,SubStruct1SubStruct2 二选一存储,以 SubStruct2 为例,int32_t c 在前,填充4个字节后存储 double d
    • 最后存储 float f,填充4个字节以满足结构体整体对齐要求。