在 C 语言中,动态内存管理使用 stdlib.h 库中的函数:
malloc(size_t size) — 分配指定大小的内存块。内存未初始化。calloc(size_t nmemb, size_t size) — 为 nmemb 个给定大小的元素分配内存块并用零初始化。realloc(void *ptr, size_t size) — 更改先前分配的内存块的大小。free(void *ptr) — 释放先前分配的内存块。使用示例:
int *arr = (int *)malloc(10 * sizeof(int)); if (arr == NULL) { // 处理内存分配错误 } // ... 使用 arr ... free(arr);
重要的是始终检查内存分配的结果是否为 NULL,并且不要忘记调用 free 以避免内存泄漏。
以下代码的结果是什么?
int *arr = malloc(sizeof(int) * 5); free(arr); free(arr);
回答:对同一块内存的重复调用 free 会导致未定义行为(undefined behavior)。同一指针只能释放一次。
故事
在一个自动化测试系统的项目中,系统经常崩溃。罪魁祸首是系统循环,在每次通过后都忘记释放通过
malloc分配的内存。经过长期测试,系统“吃掉”了所有的内存并挂起。
故事
动态数组的实现使用了
realloc,但未检查返回结果。当失败时(realloc 返回 NULL),旧内存的指针丢失,导致内存泄漏。随后的内存操作导致了段错误。
故事
开发人员被委托集成一个过时的 C 模块,在此模块中,内存通过对同一引用的
free调用两次来释放。在大多数操作系统上没有出现错误,但在新平台上应用程序开始崩溃,原因在很久之后才发现:重复释放(double-free)。