【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

时间:2022-12-09 15:04:42

????write in front????   

????大家好,我是謓泽,希望你看完之后,能对你有所帮助,不足请指正!共同学习交流????

????2021年度博客之星物联网与嵌入式开发TOP5~2021博客之星Top100~阿里云专家博主 & 星级博主~掘金⇿InfoQ~51CTO创作者[新人创作榜No.11]~周榜393﹣总榜1024⇿全网访问量40w+????

????本文由 謓泽 原创 发布在51CTOP 如需转载还请通知⚠

????个人主页-​謓泽51Ctop的博客​????

????欢迎各位→点赞???? + 收藏⭐️ + 留言????

????系列专栏-​謓泽51Ctop的分类_51CTO博客​????

✉️我们并非登上我们所选择的舞台,演出并非我们所选择的剧本????

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

 ???? 指针的未初始化

如下代码所示↓

int* p;
*p = 10;

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

p 是一个局部的指针变量,局部变量不初始化的话,默认是为随机值的。而随机的值放在指针变量 p 里面,就会以为这里面上放的是一个随机值。而随机的值放在指针变量 p 里面上,p 就会以为这是一个随机值的地址。

解引用 *p,那么我就会当 p 里面是一块地址。然后进行访问这块空间,因为 p 里面的这个地址是随机的值,这个时候就是通过这块地址在内存中由那个地址中指向的一块空间。所以,那个地址指向空间可能不是你的。那么这个时候就会造成非法访问内存。

以上讲解,所以才会把这里的 指针变量p 称之为野指针

int a = 10;      
int* pa = &a;

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

以上指针变量的初始化√ 

指针常见错误

引用未初始化的指针变量

试图引用未初始化的指针变量是初学者最容易犯的错误。未初始化的指针变量就是"野"指针,它指向的是无效的地址

有些书上说:"如果指针变量不初始化,那么它可能指向内存中的任何一个存储单元,这样就会很危险。如果正好指向存储着重要数据的内存单元,而且又不小心向这个内存单元中写入了数据,把原来的重要数据给覆盖了,这样就会导致系统崩溃",这种说法是不正确的!如果真是这样的话就是编译器的一个严重的BUG(o゚v゚)ノ

  • 所以,指针虽好但你也得会用不然你的BUG就会满天飞

???? 指针越界访问

示例代码如下↓

#include<stdio.h>

int main(void)
{
int arr[10] = { 0 };
int i = 0;
int* p = arr; //接收arr数组首元素的地址。
for (i = 0; i <= 12; i++)
//当i=10的时候已经是非法访问内存了,因为,我数组名的常量表达式内容只有10个元素。
{
*p = i; //i每次循环赋值给指针p
p++; //指针自增+1,代指arr元素+1

//*p++ = i 也是可以,这里虽说++优先级更高,但是它是后置运算符。
}
return 0;
}

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

指针变量越界数组导致野指针问题

注意→C语言是不会本身检测数组的越界行为的。


⚔ 空指针 - NULL

NULL——空指针,用来初始化指针或者给指针赋值,可以转到定义看看。 

#define NULL    ((void *)0)  本质上 NULL 其实就是 (0)

代码如下所示↓

int* p = NULL;

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

当然,如果你不知道 p 应该初始化什么地址的时候,就直接初始化 NULL。 

注意→如果当你这里 *p = 10 的时候依然会出现问题。 

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。NULL 是在计算中具有保留的值,用于指示指针不引用有效对象。程序通常使用空指针来表示条件,例如未知长度的列表结尾或未执行某些操作; 这种空指针的使用可以与可空类型和选项类型中的 Nothing 值进行比较。 

空指针不应与未初始化的指针混淆:保证空指针与指向有效对象的任何指针进行比较。但是,根据语言和实现,未初始化的指针可能没有任何此类保证。它可能与其他有效指针相等; 或者它可能比较等于空指针。它可能在不同的时间做两件事。 

#include<stdio.h>
int main(void)
{
int a = 10;
int* pa = &a;

printf("one pa = %d\n", *pa);

*pa = 20; //此时当我们不想用它时候
*pa = (int)NULL; //就把 pa 指针置成 NULL

printf("two pa = %d\n", *pa);
return 0;
}

【C语言】指针的未初始化、指针越界访问、空指针-NULL、指针使用之前检查有效性。

编译运行结果????

  • one pa = 10
  • two pa = 0 

???? 指针使用之前检查有效性

当你指针变量不可以用的时候就把它设置成NULL,当你指针变量可以用的时候就不是NULL 

当我们对这个指针进行初始化的话,那么它就是有效的,如果没有初始化那么就是无效的

if (pa != NULL)
{
//进行使用
}
if (pa == NULL)
{
//不进行使用
}