目录
目录是我们指针总共要讲的内容,而指针内容较多,所以总共分为三篇文章
内存和地址:
计算机CPU处理数据时,需要的数据就是在内存中读取的,处理后的数据也是放回内存的,而内存又划分成一个个内存单元以更加方便管理内存空间。下面我给出一个例子来类比解释:
//日常生活中,我们经常会在手机上点餐让外卖员给我们送到家门口,如果你住在一栋有50户的楼里,但是房间没有编号,房门样式都一样,那么外卖员就需要一户一户的敲门,这样效率是不是很低,这只是一栋楼,如果有多栋,同样楼也没有编号,那外卖员效率会有多低啊!当楼有了编号,房门有了编号,外卖员就可以精准的直接找到我们的家门口,大大的提高了效率。//
这里的多栋楼就好比内存,而内存单元就是房门编号,有了它们,计算机就可以精准的读取、存放数据,提高计算机运行速度。 注:每个内存单元取一个字节大小,一个字节的大小等于八个比特位,一个比特位可以存储一个二进制数字的0或1
1Byte= 8bite
1KB = 1024Byte
1MB = 1024KB
1GB = 1024MB
1TB = 1024GB
1PB = 1024TB 上面是计算机单位常用的补充
在计算机中每个内存单元都有一个编号,这个编号也被称为地址,而在C语言中我们给地址起了个新名字就叫指针:内存单元的编号==地址==指针
(这张图要仔细阅读,可以更好地帮助我们理解编址)
编译器产生——>虚拟地址——>通过硬件+软件——>虚拟地址变成物理地址
这个我们在这不会细讲,以后学习c++的需要多了解这个,java的不作过多要求。
指针变量和地址:
在C语言中我们创建一个变量的实质就是向内存申请一块空间(下面是x86的环境
)
黄色线段围住部分就是a的4个字节的地址编号
取地址操作符&:
&是单目操作符 在上面图中&a就是拿出较小的那一个地址,009BF9DC
#include<stdio.h>
int main()
{
int a = 10;
p = &a;
return 0;
}
这个代码里将a的地址存入p中,p就叫指针变量 · 地址——指针 · 指针变量——存放地址的变量
而在上面代码中我们应该给指针变量加上变量类型:int*
#include<stdio.h>
int main()
{
int a = 10;
int * p = &a;
return 0;
}
这里*是说明p是指针变量,而int是说明p指向的对象是int类型的
//只要是存到指针变量里的东西,就会被我们认为它是地址//
当我们把数据地址存入指针变量中,之后我们便可以更快捷的找到数据
#include<stdio.h>
int main()
{
int a = 10;
int * p = &a;
*p;
return 0;
}
* 是解引用操作符,也称间接访问操作符
我们也可以通过指针修改数据,正如:
这时候也许你会觉得指针也没啥用处,就如上面代码展示,我们完全可以再给a直接赋值就行,这里我们是直接改值的,而有了指针后,我们可以间接改变它的值,改变方式就会变得多样化。在我们不方便直接赋值的时候就可以使用指针进行赋值。
指针的大小:
地址所在地址线上传输,所以在32跟地址线上可以传输32个0或1的二进制位数字,也就是4个字节,那么64根地址线也就是8个字节,下面我们来验证下:
第一幅图是x86环境的(32位环境),也就是有32条地址线,第二幅图时x64环境的(64位环境),也就是有64条地址线。
不同指针的解引用:
虽然不同指针类型大小相同,但是指针类型决定了指针进行解引用操作符的时候访问几个字节,也就是决定指针的权限。比如char可以访问1和字节,int可以访问4个字节,指针访问的时地址,也就是char类型的只能改动int类型数据的地址的一个字节大小的数据。
指针加减整数:
看下面代码演示:
char*和int*加1后的结果分别与原来结果对比,int类型的变化了4个字节,char类型的变化了1个字节,这里我们可以得出:指针类型决定了指针进行+1、-1时,一次走多远的距离。