运行时使用realloc()导致程序崩溃的原因是什么?- C语言
嘿,我来帮你揪出程序崩溃的根源——你的代码里踩了好几个C语言内存管理的经典坑,和“内存被占用”关系不大,具体问题拆解如下:
核心问题分析
1. 栈上的数组根本不能用realloc扩容
你声明的int arr[3];是栈内存分配的数组,栈内存的大小是编译期就固定死的,由操作系统自动管理,完全不允许用realloc(或者free这类堆内存操作函数)来修改它的大小。realloc只能用来调整堆上动态分配的内存(也就是用malloc/calloc手动申请的内存块)。你强行对栈指针调用realloc,属于C语言里的「未定义行为」,后续的内存操作全乱套了,崩溃是必然的结果。
2. realloc的返回值被你忽略了
就算你一开始用堆内存分配数组,现在的写法也有大问题:realloc可能会把内存块迁移到新的地址,然后返回新的指针;如果扩容失败,它会返回NULL。你直接丢掉这个返回值,继续用原来的arr指针,要么访问的是已经被系统回收的旧内存,要么遇到NULL指针直接触发崩溃。
3. 循环变量i没提前声明
你的for(i = 0; i < 10; i++)里的i根本没声明,在标准C里这会导致编译错误(除非用非常老旧的编译器模式),虽然你说赋值能进行,但这也是潜在的未定义行为风险。
4. 扩容时没计算正确的字节数
realloc的第二个参数是总字节数,不是元素个数。你原来写的realloc(arr, num_of_elements),相当于只申请了num_of_elements个字节,而int类型通常占4字节,这会导致内存空间严重不足,同样会触发未定义行为。
修复后的完整代码
#include <stdio.h> #include <stdlib.h> int main() { // 改用堆内存分配初始数组,同时检查分配是否成功 int *arr = malloc(3 * sizeof(int)); if (arr == NULL) { fprintf(stderr, "初始内存分配失败!\n"); return 1; } int num_of_elements = 3; // 循环变量i直接在for循环里声明,符合标准C规范 for(int i = 0; i < 10; i++) { if(i == num_of_elements) { num_of_elements += 10; // 先用临时指针接收realloc的返回值,避免分配失败丢失原指针 int *temp_ptr = realloc(arr, num_of_elements * sizeof(int)); if (temp_ptr == NULL) { fprintf(stderr, "数组扩容失败!\n"); free(arr); // 失败时要释放原内存,避免内存泄漏 return 1; } arr = temp_ptr; // 更新数组指针为新的地址 } arr[i] = i + 10; printf("%d\n", arr[i]); } free(arr); // 堆内存一定要记得手动释放 return 0; }
额外提醒
- 永远别对栈上的变量(栈数组、局部变量的地址)使用
malloc/realloc/free,这些函数只针对堆内存。 - 每次调用
realloc都必须检查返回值,防止分配失败导致的崩溃和内存泄漏。 - 如果是用指针指向堆数组,别用
sizeof(arr)/sizeof(arr[0])计算元素个数——因为指针的sizeof是固定的(比如64位系统是8字节),这个公式会失效,最好自己维护一个变量记录元素数量,就像你代码里的num_of_elements。
内容的提问来源于stack exchange,提问作者Emirhan G.
相关产品推荐
相关产品推荐

