资料合集下载链接:
https://pan.quark.cn/s/472bbdfcd014
谈到C语言,我们永远绕不开一个强大而又“危险”的概念——指针。指针是C语言的灵魂,它赋予了我们直接操控内存的能力,带来了无与伦比的性能和灵活性。然而,“能力越大,责任越大”,稍有不慎,指针就会变成程序崩溃和各种诡异Bug的根源。
错误一:指针偏移后直接释放——“迷路的野指针”
这是初学者在进行动态内存操作时最容易犯的错误之一。
问题描述:
我们使用 malloc
等函数申请了一块堆内存,系统会返回这块内存的起始地址。我们将这个地址保存在一个指针中。在后续操作中,我们可能会移动这个指针去访问内存的不同部分(即指针偏移)。但问题是,当我们调用 free
函数时,必须传入当初 malloc
返回的那个原始的、未经改动的起始地址。如果你传入一个偏移过的地址,free
函数将无法正确工作,轻则内存泄漏,重则程序直接崩溃。
错误代码案例:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void process_string() {
// 1. 申请100字节的内存,p_origin 保存了这块内存的“门牌号”
char *p_origin = (char *)malloc(100);
if (p_origin == NULL) {
printf("内存申请失败!\n");
return;
}
printf("内存申请成功,原始地址: %p\n", p_origin);
// 2. 拷贝字符串
strcpy(p_origin, "hello world");
// 3. 为了处理字符串,我们移动了指针
// 错误操作:直接在原始指针上进行偏移
p_origin += 6; // 指针移动到了 'w' 的位置
printf("指针偏移后,指向内容: '%s', 当前地址: %p\n", p_origin, p_origin);
// 4. 释放内存——灾难发生点!
// free函数接收到的不是内存的起始地址,而是中间某个位置的地址
printf("尝试释放偏移后的指针...\n");
free(p_origin);
printf("释放完成(这句话可能永远不会被打印出来)。\n");
}
int main() {
process_string();
return 0;
}
运行结果(在典