局部变量在栈上分配空间
- 过程:
- 当函数被调用时,系统会为该函数在栈上分配一块栈帧空间。栈帧中包含函数的参数、局部变量等信息。
- 局部变量按照其声明顺序依次在栈帧内分配空间。例如,以下代码:
void func() {
int a;
double b;
}
- 先为
int
类型的变量a
分配4个字节(假设为32位系统)的栈空间,接着为double
类型的变量b
分配8个字节的栈空间。
- 栈是从高地址向低地址增长(大多数系统),分配的空间在函数调用结束时,栈帧被销毁,局部变量占用的栈空间被自动释放。
栈上局部变量与堆上动态分配内存(new
关键字)的不同
- 生命周期:
- 栈上局部变量:
- 其生命周期与函数调用紧密相关。在函数被调用时创建,函数结束时销毁。例如:
void func() {
int localVar = 10;
// localVar在此处存在
}
// 函数结束,localVar被销毁
- 堆上动态分配内存(
new
关键字):
- 由程序员手动控制其生命周期。使用
new
关键字分配内存后,直到使用delete
关键字释放内存,这块内存才会被回收。例如:
int* heapVar = new int(20);
// heapVar指向的内存一直存在,直到执行delete操作
delete heapVar;
- 内存管理方式:
- 栈上局部变量:
- 内存管理由系统自动完成。系统在函数调用和结束时,自动分配和释放栈帧空间,程序员无需手动干预。例如函数
func
中声明的局部变量,函数结束时,它们占用的栈空间自动释放。
- 堆上动态分配内存(
new
关键字):
- 需要程序员手动管理。如果使用
new
分配了内存,却没有对应的delete
操作,就会导致内存泄漏。例如以下代码:
void leakMemory() {
int* ptr = new int(30);
// 这里没有delete ptr,会导致内存泄漏
}
- 同时,使用
delete
释放内存后,指针应该置为nullptr
,防止成为野指针,例如:
int* heapVar = new int(40);
delete heapVar;
heapVar = nullptr;