当前位置: 首页 > 文档资料 > C 语言程序设计 >

野指针和空指针

优质
小牛编辑
147浏览
2023-12-01

指针变量也是变量,是变量就可以任意赋值,不要越界即可(32位编译器指针大小为4字节,64位编译器指针大小为8字节),但是,任意数值赋值给指针变量没有意义,因为这样的指针就成了野指针,此指针指向的区域是未知(操作系统不允许操作此指针指向的内存区域)。所以,野指针不会直接引发错误,操作野指针指向的内存区域才会出问题。

int a = 100;
int *p;
p = a; //把a的值赋值给指针变量p,p为野指针, ok,不会有问题
p = 0x12345678; //给指针变量p赋值, 为野指针,ok,不会有问题
p = 1000; //操作野指针指向未知区域,内存出问题,err

但是,野指针和有效指针变量保存的都是数值,为了标志此指针没有指向任何变量(空闲可用),C语言中,可以把NULL赋值给此指针,这样标志此指针为空指针,没有任何指向。

int *p = NULL;

NULL是一个值为0的宏常量

#define NULL ((void *)0)

NULL到底是什么

1500217329455

本质上是一个宏定义,在C语言中NULL本质是0,但是这个0不是当一个数字来解析,而是当一个内存地址来解析的,这个0其实就是0x00000000,代表内存的0地址。

NUL是ASCII码表的第一个字符,表示的是空字符,其ASCII码值为0

(void *)0这个整体表达式表示一个指针。这个指针变量本身占四个字节,地址指向哪里取决于指针变量本身,这个指针变量的值是0,也就是说这个指针变量指向0地址(实际是0地址开始的一段内存)

#ifdef __cplusplus
#define NULL 0
#else
#define NULL ((void *)0)
#endif
int *p = NULL; // p的值是(void *)0的值,实际就是0,意思是指针p指向内存的0地址处

1499701976789

野指针

指向不可用区域的指针被称为野指针。对野指针进行操作可能会发生不可预知的错误。野指针的形成原因有以下两种:

  • 指针变量没有被初始化。定义的指针若没有被初始化,则可能指向系统中任意一块存储空间,若指向的存储空间正在使用,当发生调用并执行某种操作时,就可能造成系统崩溃。
  • 若两个指针指向同一块存储空间,指针与内存使用完毕之后,调用相应函数释放了一个指针与其指向的内存,却未改变另一个指针的指针,将其置空。

在编程时,可以通过“if(p==NULL){}”来判断指针是否指向空,但是无法检测该指针是否为野指针,所以要避免野指针的出现。

1.野指针

野指针:没有进行初始化操作的指针-->由于该指针变量内部所存储的地址是个随机值,因此是野地址(类型含义:指针)

注:指针类型的变量必须在其被创建的时候就需要进行初始化操作,否则就成了野指针,所谓野指针就是乱指向的指针,形成的就是一个随机垃圾地址

2.胡乱使用野指针所造成的现象:

(1).指向驱动程序所属内存,将会出现蓝屏现象

(2).指向普通的应用程序,会将本身的这个应用程序结束掉

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

int main01(void)
{
    int * p;
      printf("%d \n", *p);
    system("pause");
}

野指针产生的原因

指针变量和它所指向的内存空间变量是两个不同的概念

释放了指针所指的内存空间 但是指针变量本身没有重置成NULL

避免方法:

(1)定义指针的时候 初始化成NULL

(2)释放指针所指向的内存空间后,把指针重置成NULL

void main()
{
    char  *p1 = NULL;
    p1 = (char *)malloc(100);
    if (p1 == NULL)
    {
        return ;
    }
    strcpy(p1, "12345");

    printf("p1:%s \n", p1);

    if (p1 != NULL)
    {
        free(p1);
        p1 = NULL;
    }

    if (p1 != NULL)
    {
        free(p1);
    }

    system("pause");
    return ;
}