我能“C”——初阶指针(上)

目录

1.什么是指针?

2. 指针和指针类型  

3.野指针

3.1野指针的成因

3.2 如何规避野指针


1.什么是指针?

指针理解的 2 个要点:
1. 指针是内存中一个最小单元的编号,也就是地址
2. 平时口语中说的指针,通常指的是指针变量,是用来存放内存地址的变量

总结:指针就是地址,口语中说的指针通常指的是指针变量

总结:
指针变量,用来存放地址的变量。(存放在指针中的值都被当成地址处理)。
那这里的问题是:
  • 一个小的单元到底是多大?(1个字节)
  • 如何编址?
经过仔细的计算和权衡我们发现一个字节给一个对应的地址是比较合适的。 对于32位的机器,假设有32根地址线,那么假设每根地址线在寻址的时候产生高电平(高电压)和低电 平(低电压)就是(1或者0);那么32根地址线产生的地址就会是:
00000000 00000000 00000000 00000000
00000000 00000000 00000000 00000001
...
11111111 11111111 11111111 11111111
这里就有232次方个地址。
每个地址标识一个字节,那我们就可以给 (2^32Byte==2^32/1024KB == 2^32/1024/1024MB==2^32/1024/1024/1024GB == 4GB) 4G的空间进行编址。

这里我们就明白:
  • 32位的机器上,地址是320或者1组成二进制序列,那地址就得用4个字节的空间来存储,所以
  • 一个指针变量的大小就应该是4个字节。
那如果在 64 位机器上,如果有 64 个地址线,那一个指针变量的大小是 8 个字节,才能存放一个地
址。
总结:
  • 指针变量是用来存放地址的,地址是唯一标示一个内存单元的。
  • 指针的大小在32位平台是4个字节,在64位平台是8个字节。

2. 指针和指针类型  

 不管是什么类型的指针,大小都是4个字节(x86环境)。但是在x64环境下为8个字节。

这里我们在讨论一下:指针的类型
我们都知道,变量有不同的类型,整形,浮点型等。那指针有没有类型呢?
准确的说:有的。
第一个意义:
——>指针类型决定了在解引用指针的时候能访问几个字节
调试下看看:先用int*的类型

 刚开始是44 33 22 11再按F10调试:

 结果都变成00 00 00 00

现在用char类型试试:

 刚开始是44 33 22 11(这里int a 和char*不同类型会小报个警告,先不管他)

再继续调试:

结果变成了00 33 22 11和刚刚的int类型不一样这就是区别。 

当是int的时候直接改了4个字节,当时char的时候只改了1个字节

所以:指针类型决定了在解引用指针的时候能访问几个字节

 第二个意义:

——>指针类型决定了,指针进行+1 、 -1的时候,一步走多远

比如: char* 的指针解引用就只能访问一个字节,而 int* 的指针的解引用就能访问四个字节。

 为什么会这样?因为pa认为它指向的是一个整型,所以当给pa加上1的时候就是说我访问完了这个整型就要跳到下一个整型,所以就跳了一个整型

但是对于char来说加上1就是跳过一个字符就是一个字节嘛,所以加了个1。

等价图:

所以:指针类型决定了,指针进行+1 、 -1的时候,一步走多远

总结:

指针的类型决定了,对指针解引用的时候有多大的权限。(能操作几个字节)

问:学这些有什么用??

现在放了10个0 ,现在我想把它们初始化到1—10

 用指针依次访问元素,我当我对它解引用操作的时候访问正好一个整型,访问下一个必须要跳一步,我对它解引用的时候想访问4个字节,所以用整型指针是最合适的。

 *p解引用操作一次访问4个字节(一个整型元素)  p++ 加1操作   |    跳过一个整型,所以这里只有int可以胜任  

要是改成char:

 

 3.野指针

概念:野指针就是指针指向的位置是不可知的(随机的、不正确的、没有明确限制的)

3.1野指针的成因

1.指针未初始化 

 这里的p没有初始化就随机选了个地址,就会造成非法访问。就比如说你大晚上很困,你回不了家了就随便去陌生人的家里倒头就睡是不是私闯民宅?

2.指针越界访问 

 如图前10个指针还是正常的,但是这里的循环是到i=12,明显就越界了,越界的那一部分就变成了野指针。

 3.指针指向的空间释放(略)

卖关子,放到动态内存开辟的时候再讲。

3.2 如何规避野指针

1.指针初始化

2.小心指针越界

3.指针指向空间释放,及时置NULL

4.避免返回局部变量的地址

5.指针使用之前检查有效性

#include <stdio.h>
int main()
{
    int *p = NULL;
//一个指针不知道指向哪里的时候,暂时可以初始化为NULL;
    //....
    int a = 10;
    p = &a;
    if(p != NULL)
   {
        *p = 20;
   }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/Yzl17841857589/article/details/129794651