代码运行一万遍和运行十万遍耗时一样吗

Posted 代二毛

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了代码运行一万遍和运行十万遍耗时一样吗相关的知识,希望对你有一定的参考价值。

前言

在B站刷视频的时候看到一个视频,讲的是阿里的一道面试题,觉得很兴趣,在此总结一下。原视频链接:https://www.bilibili.com/video/BV1tv411J7Ap。

问题描述

int i = 0;
int length= 64*1024*1024;
int * arr = (int *)molloc(length);

//循环1
for(i = 0; i < length; i++)
{
	arr[i] *=3;
}

//循环2
for(i = 0; i < length; i +=16)
{
	arr[i] *=3;
}

问题:上面两个循环的耗时相差多少?

问题分析:

1.分析:代码中定义了(60 x 1024 x 1024)个成员的数组,循环1是去遍历所有的成员,循环2是访问1/16的成员。如果耗时和访问次数成线性关系,那么循环2的耗时大约是循环1的16倍;如果不是线性关系,那又是什么原因导致了差异。

问题解决的步骤

1.简单粗暴的验证。直接用代码去测试,发现这两个循环的耗时,相差无几,说明耗时和访问次数不是简单的线性关系。现在已经得到了结论,接下来就是找寻理论依据去支撑这个结论。
2.理清影响耗时的因素。运行代码的过程,大致是把数据从内存读到CPU进行处理,然后写回内存。其中CPU的运行速度是远大于内存的运行速度,读取内存会占用大部分的时间。
3.两个循环访问内存的次数会相差16倍吗?很显然不是的,要不然时间就不会相差无几了。原因是cache的存在,cache分为iCache和dCache,不了解的可以参考博客《ARM芯片开发学习(S5PV210)——icache、dcache介绍和如何开关icache》。CPU去访问一次内存,会将一段数据读到cache里,之后需要数据就先去cache里查找,找不到再去读取内存,而不是每次都要去读内存。cache与内存之间的数据交互是缓存行为单位的,x86架构的缓存行是64字节,16个int型变量刚好64字节,无论你需要读取1个int型变量,还是读取16个int型变量,cache和内存都会交互64字节,所以这两者的耗时没有明显区别。
4.补充:这类似于平时写C语言代码里,用char型变量和int型变量其实耗时都差不多。假设现在是32位的机器,int占4字节,char占1字节,但是无论你访问的是char型变量还是int型变量,CPU都会一次读取4字节内容。

以上是关于代码运行一万遍和运行十万遍耗时一样吗的主要内容,如果未能解决你的问题,请参考以下文章

使用Java写出一万遍我爱你(while循环和do——while循环)

使用Java写出一万遍我爱你(while循环和do——while循环)

maven存在编译bug

Solr介绍

已经说过千万遍了!!面试官,不要再问我三次握手和四次挥手了

循环语句介绍