第十章:内存管理详解(堆、栈、new/delete、RAII)
·
目录
四、C 语言 malloc/free vs C++ new/delete
一、为什么 C++ 内存管理如此重要?
在 C++ 中:
-
程序员直接控制内存的申请与释放
-
灵活但危险
-
一旦出错,轻则程序崩溃,重则产生安全漏洞
常见问题包括:
-
内存泄漏
-
野指针
-
重复释放
-
越界访问
理解内存模型,是写好 C++ 的必经之路
二、内存的四大区域(重点)
一个 C++ 程序运行时,内存大致分为以下区域:
1.栈区(Stack)
特点:
-
存放:局部变量、函数参数
-
由编译器自动分配和释放
-
速度快,空间小
-
生命周期随作用域结束
void func() {
int a = 10; // 栈变量
}
2.堆区(Heap)
特点:
-
由程序员手动申请和释放
-
生命周期不受作用域限制
-
空间大,但管理成本高
int* p = new int(10);
delete p;
3.全局/静态区
-
全局变量
-
静态变量
-
生命周期贯穿整个程序
int g_val = 10;
void test() {
static int s = 5;
}
4.常量区
-
字符串常量
-
const 修饰的常量
const int c = 10;
三、栈内存 vs 堆内存
| 对比项 | 栈 | 堆 |
|---|---|---|
| 管理方式 | 自动 | 手动 |
| 生命周期 | 作用域 | 程序员控制 |
| 速度 | 快 | 相对慢 |
| 空间 | 小 | 大 |
| 安全性 | 高 | 低(易出错) |
优先使用栈,必要时才使用堆
四、C 语言 malloc/free vs C++ new/delete
1.malloc/free(C 风格)
int* p = (int*)malloc(sizeof(int));
*p = 10;
free(p);
缺点:
-
不调用构造函数
-
类型不安全
-
使用繁琐
2.new/delete(C++ 推荐)
int* p = new int(10);
delete p;
优点:
-
自动调用构造 / 析构函数
-
类型安全
-
语义清晰
3.new[] / delete[](数组)
int* arr = new int[5];
delete[] arr; // 必须成对使用
⚠️ new[] 一定要搭配 delete[]
五、常见内存错误
1. 内存泄漏
void func() {
int* p = new int(10);
// 忘记 delete
}
正确做法:
-
成对使用 new/delete
-
使用 RAII / 智能指针
2. 野指针
int* p;
*p = 10; // 未初始化
解决:
int* p = nullptr;
3. 悬空指针
int* p = new int(10);
delete p;
*p = 20; // 错误
建议:
delete p;
p = nullptr;
4. 重复释放
delete p;
delete p; // 未定义行为
六、RAII:C++ 内存管理的核心思想
1.什么是 RAII?
RAII(Resource Acquisition Is Initialization)
资源的获取与对象的生命周期绑定
-
构造函数:申请资源
-
析构函数:释放资源
2.RAII 示例
class MyInt {
public:
MyInt(int val) {
data = new int(val);
}
~MyInt() {
delete data;
}
private:
int* data;
};
void test() {
MyInt obj(10); // 自动申请
} // 自动释放
优点:
-
不易泄漏
-
异常安全
-
代码更简洁
STL 容器、智能指针,底层全是 RAII
七、最佳实践总结
- 能用栈就不用堆
- new/delete 成对出现
- delete 后指针置 nullptr
- 避免裸指针长期持有资源
- 优先使用 STL 和智能指针
更多推荐



所有评论(0)