- 数组越界:
int arr[3] = {1, 2, 3};
arr[3] = 4; // 数组越界
for (int i = 0; i <= 3; i++) {
printf("%d\n", arr[i]); // 数组越界
}
在上述代码中,由于数组下标从0开始,arr[3]越界访问了数组最后一个元素的位置,此时程序可能会崩溃或者产生其他不确定的结果;另外在循环中因为i<=3条件中使用了小于等于号,导致循环访问到了数组最后一个元素之后的位置,同样也引起了数组越界问题。
- 指针问题:
int *p;
int a = 10;
*p = a; // 指针未初始化
int arr[3] = {1, 2, 3};
p = &arr[3]; // 指针越界
int *q = NULL; // 空指针
*q = 10;
在上述代码中,第一个例子中,指针p未初始化就被用来存储变量a的地址,这将导致未知的结果;第二个例子中,指针p超出了数组索引的范围,指向了不存在的地址,同样会导致未知的结果;第三个例子中,指针q初始化为NULL,但是仍然被用来存储变量10,这是一个空指针引用问题,可能会导致程序崩溃。
- 内存泄漏:
void func () {
int *p = (int *)malloc(sizeof(int));
// do something
return; // 遗漏了释放内存
}
在上述代码中,函数func()中使用了动态内存分配函数malloc分配了一段内存,但却没有在函数结束后手动释放这段内存,造成内存泄漏。
- 循环陷阱:
int i = 0;
do {
printf("%d\n", i);
} while (i++ < 5); // 条件不当
int j = 0;
while (j >= 0) { // 计数器错误
j++;
}
在上述代码中,第一个例子中,循环条件中使用了后缀自增运算符,导致循环结束后,i的值又增加了1;第二个例子中,计数器j一直增加,但由于j是无符号整型变量,所以它永远不会小于0,会导致死循环。
- 悬垂指针:
int *p;
{
int a = 10;
p = &a; // 悬垂指针
}
*p = 20;
在上述代码中,指针p被用来存储局部变量a的地址,但是当函数块结束后,变量a被销毁了,此时指针p被称为悬垂指针,它指向已经被释放的内存区域,在使用它的时候可能会引起不可预料的问题。
标签:10,arr,int,代码,越界,例子,内存,陷阱,指针 From: https://blog.51cto.com/u_15903730/6408437