C/C++内存管理
代码段(Text Segment) 内容:编译后的机器指令(如函数 main()、printf() 的代码)。属性:只读(防止程序意外修改指令),可被多个进程共享(节省内存)。数据段(Data Segment) 初始化数据:显式初始化的全局/静态变量。代码语言:javascriptAI代码解释代码语言:javascriptAI代码解释堆(Heap) 动态内存:通过分配,需。代码语言:javascr
代码段(Text Segment) 内容:编译后的机器指令(如函数 main()、printf() 的代码)。 属性:只读(防止程序意外修改指令),可被多个进程共享(节省内存)。
数据段(Data Segment) 初始化数据:显式初始化的全局/静态变量。
代码语言:javascript
AI代码解释
int global_init = 42; // 存储在 Data Segment
static int static_init = 5;
BSS 段 未初始化数据:未显式初始化的全局/静态变量,程序启动时自动清零。
代码语言:javascript
AI代码解释
int global_uninit; // 存储在 BSS 段(实际值为 0)
static int static_uninit;
堆(Heap) 动态内存:通过 malloc、calloc、realloc 分配,需手动释放。
代码语言:javascript
AI代码解释
int *arr = malloc(100 * sizeof(int)); // 堆上分配
free(arr); // 必须显式释放
特点:
- 地址增长方向:低地址 → 高地址。
- 分配速度较慢(需维护空闲内存链表)。
- 可能产生碎片或内存泄漏。
栈(Stack) 自动管理:存储局部变量、函数参数、返回地址等。
代码语言:javascript
AI代码解释
void foo() {
int local_var = 10; // 栈上分配
}
特点:
- 地址增长方向:高地址 → 低地址(与堆相反)。
- 分配/释放速度快(仅移动栈指针)。
- 大小有限(可能栈溢出,如无限递归)。

关键注意事项: **栈溢出:**递归过深或局部变量过大导致栈空间耗尽(如 int arr[1000000];)。
**堆管理:**忘记 free 会导致内存泄漏;重复释放或越界访问会引发崩溃。
**全局变量:**过多使用会增加程序启动时间和内存占用。
地址大小关系,通常符合: 代码段 < Data 段 < BSS 段 < 堆 < 栈。
看一道题来加深理解,代码如下:
代码语言:javascript
AI代码解释
int globalVar = 1;
static int staticGlobalVar = 1;
void Test()
{
static int staticVar = 1;
int localVar = 1;
int num1[10] = { 1, 2, 3, 4 };
char char2[] = "abcd";
char* pChar3 = "abcd";
int* ptr1 = (int*)malloc(sizeof (int)* 4);
int* ptr2 = (int*)calloc(4, sizeof(int));
int* ptr3 = (int*)realloc(ptr2, sizeof(int)* 4);
free(ptr1);
free(ptr3);
}

在这里插入图片描述

简单来说,在一般情况下,在栈区开辟空间,先开辟的空间地址较高,而在堆区开辟空间,先开辟的空间地址较低。 注意:在堆区后一个开辟的空间的地址不一定比前面先开辟空间的地址大,因为可能后开辟空间的地址是在前面释放的空间上开辟的地址。
记住: sizeof是一个C语言中的一个单目运算符,而strlen是一个函数,用来计算字符串的长度。sizeof求的是数据类型所占空间的大小,而strlen是求字符串的长度,strlen(结束的标志是是否碰到\0)。

在这里插入图片描述

在这里插入图片描述
二、C语言中动态内存管理
1、malloc / calloc / realloc 和 free
malloc
malloc函数的功能是开辟指定字节大小的内存空间,如果开辟成功就返回该空间的首地址,如果开辟失败就返回一个NULL。传参时只需传入需要开辟的字节个数。
calloc
calloc函数的功能也是开辟指定大小的内存空间,如果开辟成功就返回该空间的首地址,如果开辟失败就返回一个NULL。calloc函数传参时需要传入开辟的内存用于存放的元素个数和每个元素的大小。calloc函数开辟好内存后会将空间内容中的每一个字节都初始化为0。
realloc
realloc函数可以调整已经开辟好的动态内存的大小,第一个参数是需要调整大小的动态内存的首地址,第二个参数是动态内存调整后的新大小。 realloc函数与上面两个函数一样,如果开辟成功便返回开辟好的内存的首地址,开辟失败则返回NULL。

在这里插入图片描述
free
free函数的作用就是将malloc、calloc以及realloc函数申请的动态内存空间释放,其释放空间的大小取决于之前申请的内存空间的大小。
更多推荐



所有评论(0)