编程代码
新闻详情

「C++」读懂指针与内存

发布时间:2021-01-18 09:08:08 浏览次数:2084

C和C++最强大的地方在哪里呢?就是指针对内存的操作。有了指针我们才可以在代码内存里自由飞翔,想玩哪里玩哪里,想变什么变什么。


内存
首先我们聊聊什么是内存(我们以32位程序模型为例)。对于一个进程来说,内存可以理解成一连串的带编号的存储区域。

每个进程都映射一段连续的虚拟内存地址(不是内存的真实物理地址,只是一个编号,物理内存地址可以不连续)。

「C++」读懂指针与内存

每个格子我们理解为一个字节,也就是一个byte或者说一个unsigned char。


而指针其实就是一个数字,记录的就是内存的地址,也就是我们标记的每个小格子的数字编号。

在32位系统的时候,指针占4个字节,能表示的数字最大值是4294967295。

(64位程序指针占8个字节,所以能使用的内存空间就很大)

「C++」读懂指针与内存

「C++」读懂指针与内存

将4294967295个字节转换G单位大概就是4G。所以32位程序能用的最大内存空间就是4G。其中0到3G是用户空间,3G到4G是内核空间,我们在实际使用32位程序时候,大概也就能操作到1.7G左右的内存,超过这个量再分配内存基本上程序就崩溃了。


程序的内存区域大概分了如图六块,其中堆和栈是根据实际运行情况扩展使用内存区域。

「C++」读懂指针与内存

来来来。。我们写段代码验证下,都用int变量,偏移量是4个字节,方便查看。

看看运行结果,内存地址就是这样按照区域分配的。

「C++」读懂指针与内存

「C++」读懂指针与内存

指针

明白了内存,我们就来玩玩指针,看他怎么个自由飞翔。

先上一段朴实的代码:

「C++」读懂指针与内存

运行结果是这样的:

「C++」读懂指针与内存

让我们来分析下这段代码吧。


为了方便使用结构体倒腾,我这里都用的是4倍体的变量,而且把double放在了第一个。关于结构体排列问题有机会我再写写。反正这里呢,就按照这几个位置排列内存了。


首先我们整了一个100字节的内存,神马都没有,然后通过指针和偏移量,我们可以跳转到内存任意位置,并且可以把那个位置解释成任意类型。所以指针可以是8字节的double类型,也可以是4字节的int和float类型,然后对该类型直接赋值。

最后,我们直接来个风骚操作,把这段内存强制当成结构体类型的指针,然后因为位置能对上,所以结构体内的成员变量就都对应上了。


然后我们再来玩一玩快乐指针的游戏,依然使用刚才内存倒腾过的区域。

「C++」读懂指针与内存

这里p指向了b变量的位置,此时我们可以把p当成一个int数组,所以p[3]就是该数组第四个元素,也就是变量e。

「C++」读懂指针与内存

这里p+2表示按照指针类型移动2个位置,int是4个字节,所以内存上总共移动8个字节,到了d的位置,虽然位置对了,但是d不是一个int类型,按照int去解释是错误的。所以我们把类型解释成float。

「C++」读懂指针与内存

当然因为float也是4个字节,所以我们可以p[2]直接取到d位置的值,此时这里是解释出来的int值是错误的,然后我们取地址变成指针,再强转成float指针,再取值,结果一样。


记住。。。指针就是地址数字而已,可以转成任意类型,可以按照指针对应类型的大小做加减法偏移,也可以按照指针对应类型的大小做数组偏移。

在线客服 双翌客服
客服电话
  • 0755-23712116
  • 13822267203