C++面试4-sizeof解析
C++sizeof
关键字的深度解析
一、本质认知:编译器的尺度
1. 编译期操作符的基因
int arr[5];
cout << sizeof(arr); // 输出20(假设int为4字节)
- 非运行时特性:在编译阶段完成计算,不会生成任何机器指令
- 表达式不求值:
sizeof(++i)
不会改变i的值 - 类型感知:对类型名使用时必须加括号(
sizeof(int)
合法,sizeof int
非法)
2. 底层原理映射表
操作对象 | 编译器行为 | 典型示例 |
---|---|---|
基本类型 | 直接查类型系统元数据 | sizeof(int)→4 |
类对象 | 计算所有成员总大小+对齐填充 | class A{int x;};→4 |
指针 | 返回地址长度(与类型无关) | sizeof(char*)→8 (64位系统) |
数组 | 计算整个数组内存容量 | int arr[5];→20 |
二、类与对象的暗战:内存布局的密码
1. 空类的生存法则
class Empty {};
cout << sizeof(Empty); // 输出1(编译器插入占位字节)
- 存在性证明:确保不同实例有独立地址
- 继承时的优化:空基类优化(EBO)可消除大小开销
2. 虚函数的代价
class Base { virtual void foo(){} };
cout << sizeof(Base); // 输出8(64位系统vptr指针)
- 虚表指针(vptr):每个多态类携带隐形成员
- 多重继承倍增:每层虚继承增加一个vptr
3. 内存对齐的暴政
struct Weird {char c; // 1字节// 3字节填充int i; // 4字节double d; // 8字节
};
cout << sizeof(Weird); // 输出1+3+4+8=16(实际可能更大)