C语言中野指针问题

一、什么是野指针

野指针:

         是指向无效或未定义内存地址的指针,其值通常是随机的、不确定的,可能指向已被释放的内存、未初始化的区域或非法地址
。与空指针(NULL)不同,野指针本身并不是NULL,而是指向无法正常访问的内存空间,操作野指针可能导致程序崩溃或数据损坏

二、野指针与空指针的区别

特征               野指针                                              空指针(NULL)
​定义​          指向无效或随机地址的指针                  显式赋值为NULL的指针
​安全性​      危险,可能导致崩溃或错误                  安全,解引用会明确报错
​成因​          未初始化、释放后未置空等                  开发者主动赋值NULL
​处理方式​      需通过初始化或置空规避                  可通过条件判断避免误用

三、代码示例

#include <stdio.h>
#include <stdlib.h>

/*
1.返回局部变量的地址:函数返回局部变量的地址时,局部变量生命周期结束后内存会被回收
int* test() {
    int n = 100;
    return &n; // 返回局部变量地址
}
int* p = test(); // p成为野指针
改正:改用动态内存分配或静态变量:
*/
int* getIntPointer(int value) {
    static int* size = NULL;
    int* ptr = malloc(sizeof(int));
    if (ptr == NULL) {
        fprintf(stderr, "Memory allocation failed\n");
        return NULL;
    }
    *ptr = value;
    return ptr,size;
}

int main()
{
    //野指针的成因
    // 2.指针未初始化:此时p指向未知区域,解引用可能导致段错误
    //int* p;  // 未初始化,p为野指针
    //*p = 10; // 非法访问随机地址
    // 改正:1、未明确指向时初始化为NULL
    //      2、显式赋值有效地址:int *p = &valid_var
    int* p = NULL;

    // 3.​指针指向已释放的内存
    //int* p = (int*)malloc(sizeof(int));
    //free(p);  // 释放内存
    //*p = 20;  // p仍指向已释放的地址,成为野指针
    // 改正:释放内存后置空指针
    int* p2 = (int*)malloc(sizeof(int));
    if (p2==NULL) {
        printf("内存分配失败\n");
        return -1;
    }
    else {
        printf("内存分配成功\n");
        *p2 = 20;  // 正确访问已分配的内存
        p2 = NULL; // 释放后置空
    }

    //​ 4.指针越界访问:访问超出数组范围的地址时,指针指向非法内存:
    //int arr[10] = {0};
    //int* p = arr;
    //for (int i = 0; i <= 11; i++) {
    //    *(p++) = i; // 越界后p成为野指针
    //}
    // 改正
    int arr[10] = {0};
    int* arr_p = arr;
    for (int i = 0; i <= 11; i++) {
        *(arr_p++) = i; // 越界后p成为野指针
    }

    return 0;
}

四、野指针的成因及预防方法

1,成因:返回局部变量的地址:函数返回局部变量的地址时,局部变量生命周期结束后内存会被回收

      预防:改用动态内存分配或静态变量

2, 成因:指针未初始化:此时p指向未知区域,解引用可能导致段错误

      预防:

              a、未明确指向时初始化为NULL
              b、显式赋值有效地址:int *p = &valid_var

3,成因:指针指向已释放的内存

      预防: 释放内存后置空指针

4, 成因:指针越界访问:访问超出数组范围的地址时,指针指向非法内存

      预防:数组遍历是声明合适大小的的循环变量

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值