【第三章:BAT等名企面试真题解析8讲】第11节:阿里面试真题解析之内存对齐
前言
阿里的面试非常的喜欢问体系结构相关的问题。比如我在秋招面阿里云polardb团队终面当中被问到的这个问题:
你知道什么是内存对齐以及为什么要内存对齐么?
相信大家都思考或者看到过这个问题,看似离我们平时写代码很远的细节却能考察出我们对计算机体系结构的了解,这也是为什么在阿里的面试当中会出现这个问题的原因。接下来我将会通过几个例子讲解我对内存对齐的理解,然后以阿里面试真题为例对内存对齐相关问题进行解析。
内存对齐
内存对齐:编译器将程序中的每个“数据单元”安排在适当的位置上。
简单理解:按照某种规则将我们定义的结构体成员放在合适的地址偏移位置上存储。
举一个例子:
//32位系统 #include<iostream> using namespace std; struct{ int x; char y; }s; int main() { cout << sizeof(s) << endl; return 0; }
问题:上述代码的输出是多少?
答案:8
为什么要额外的3字节去填充这个结构体?一个原本5字节的结构现在变成8 字节,几乎扩大了 2 倍的存储空间,这样的空间开销是否值得?又是什么样的原因导致这样的设计?
内存对齐的原因
1.内存以字节为单位:
内存是以字节为单位存储,但是处理器并不会按照一个字节为单位去存取内存。处理器存取内存是块为单位,块的大小可以是2,4,8,16字节大小,这样的存取单位称为内存存取粒度。如果在64位的机器上,不论CPU是要读取第0个字节还是要读取第1个字节,在硬件上传输的信号都是一样的。因为它都会把地址0到地址7,这8个字节全部读到CPU,只是当我们是需要读取第0个字节时,丢掉后面7个字节,当我们是需要读取第1个字节,丢掉第1个和后面6个字节。所以对于计算机硬件来说,内存只能通过特定的对齐地址进行访问。
2.内存存取效率:
从内存存取效率方面考虑,内存对齐的情况下可以提升CPU存取内存的效率。比如有一个整型变量(4 字节),现在有一块内存单元: 地址从 0~7。这个整型变量从 地址为 1 的位置开始占据了 1,2,3,4 这 4 个字节。 现在处理器需要读取这个整型变量。假设处理器是 4 字节 4 字节的读取,所以从 0 开始读读取 0,1,2,3发现并没有读完整这个变量,那么需要再读一次,读取 4,5,6,7。然后对两次读取的结果进行处理,提取出 1,2,3,4 地址的内容。需要两次访问内存,同时通过一些逻辑计算才能得到最终的结果。如果进行内存对齐,将这个整型变量放在从0开始的地址存放,那么CPU只需要一次内存读取,并且没有额外的逻辑计算。可见内存对齐之后存取的效率提升了1倍。
面试真题
1.C++当中一个空的结构体或者类的对象的大小是多少?
剩余60%内容,订阅专栏后可继续查看/也可单篇购买
<p> 《收割BAT:C++校招学习路线总结》,专刊共计17节。专刊分为五大主要内容,包括后台开发学习路线、简历制作,面试技巧、BAT等名企面试真题解析和工作学习常用工具。本专刊将介绍我在技术成长过程当中的经验,通关BAT的面试技巧,并结合亲身经历的面试真题由浅入深的讲解后台开发方向的重点问题,让你们的求职之路更加顺畅。 本专刊购买后即可解锁所有章节,故不可以退换哦~ </p> <p> <br /> </p>