多重 for 循环,如何提高效率?
2258?字 14 圖 :?文章字?jǐn)?shù)
6 分鐘 :?預(yù)計(jì)閱讀
網(wǎng)絡(luò) : 內(nèi)容來源
BabyCoder :?編輯整理
前言
??我在《華為 C 語(yǔ)言編程規(guī)范》中看到了這個(gè):當(dāng)使用多重循環(huán)時(shí),應(yīng)該將最忙的循環(huán)放在最內(nèi)層。如下圖:
??由上述很簡(jiǎn)單的偽代碼可以看到,推薦使用的方式是:外小內(nèi)大的方式。也就是內(nèi)層循環(huán)是最忙的。
??然后我又在另外一份編程規(guī)范手冊(cè)中,看到了類似的要求,如下圖:
??看到了這個(gè)小技巧之后,我迫不及待的分享給我的小伙伴,后來閑下來的時(shí)候,就想自己做個(gè)測(cè)試,驗(yàn)證一下是否真的是這樣。
Ubuntu 測(cè)試
??使用 Ubuntu 14.04 的系統(tǒng)進(jìn)行測(cè)試,基本信息如下:
系統(tǒng)版本:Ubuntu14.04
gcc 版本:4.8.2
??我使用了兩份不同的代碼文件進(jìn)行測(cè)試,第一份是 外大內(nèi)小 的代碼,如下:
#include <iostream>#include <stdio.h>#include <stdlib.h>#include <sys/time.h>#include <unistd.h> using namespace std; int main(){ struct timeval tv; unsigned long ulStartTime, ulEndTime;gettimeofday(&tv, NULL); // 獲取當(dāng)前時(shí)間 ulStartTime = tv.tv_sec * 1000000 + tv.tv_usec; // 計(jì)算當(dāng)前起始時(shí)間 cout << "start time = " << ulStartTime << endl; // 打印顯示 for(unsigned int i = 0; i < 1000000; i++) // 測(cè)試代碼 { for(int j = 0; j < 100; j++) { } } gettimeofday(&tv, NULL); ulEndTime = tv.tv_sec * 1000000 + tv.tv_usec; // 計(jì)算結(jié)束時(shí)間 cout << "end time = " << ulEndTime << endl; // 打印結(jié)束時(shí)間 cout << "Time = " << ulEndTime - ulStartTime << endl; // 計(jì)算時(shí)間差值 微秒 us}??執(zhí)行上述代碼,運(yùn)行結(jié)果如下,耗時(shí):165280us
??接著,我又準(zhǔn)備了另外一份 外小內(nèi)大 的代碼,對(duì)比只是調(diào)換了 for 循環(huán)內(nèi)外層的循環(huán)次數(shù)而已,如下:
#include <iostream>#include <stdio.h>#include <stdlib.h>#include <sys/time.h>#include <unistd.h> using namespace std; int main(){ struct timeval tv; unsigned long ulStartTime, ulEndTime;gettimeofday(&tv, NULL); ulStartTime = tv.tv_sec * 1000000 + tv.tv_usec; cout << "start time = " << ulStartTime << endl; for(int i = 0; i < 100; i++) { for(unsigned int j = 0; j < 1000000; j++) {} } gettimeofday(&tv, NULL); ulEndTime = tv.tv_sec * 1000000 + tv.tv_usec; cout << "end time = " << ulEndTime << endl; cout << "Time = " << ulEndTime - ulStartTime << endl;}??上述代碼的執(zhí)行結(jié)果如下,耗時(shí):155960us
??對(duì)比上述兩份代碼的運(yùn)行結(jié)果,可以很明顯的看到,外小內(nèi)大效率更高一點(diǎn)!
??不過,你以為這就結(jié)束了嗎?
樹莓派測(cè)試
??手邊剛好有一臺(tái)樹莓派,前段時(shí)間剛安裝了最新的官方系統(tǒng),就想著拿來做一下測(cè)試,基本信息如下:
樹莓派系統(tǒng)版本:buster
g++ 版本:8.3.0
??測(cè)試代碼與在 Ubuntu 上運(yùn)行的代碼保持一致,這里就不重復(fù)貼代碼了,只看一下運(yùn)行結(jié)果。
??下邊這個(gè)是 外大內(nèi)小 的,運(yùn)行結(jié)果如下,耗時(shí):1214569us
??這個(gè)是 外小內(nèi)大 的,運(yùn)行結(jié)果如下,耗時(shí):1345193us
??完了,可以很明顯的看到,外大內(nèi)小 的運(yùn)行效率要更高一點(diǎn)。
問題分析
??我也是有點(diǎn)蒙逼的,不知道為啥會(huì)出現(xiàn)截然相反的情況,對(duì)比兩個(gè)系統(tǒng)版本,硬件設(shè)備來看,推測(cè)原因有如下幾種可能:
處理器架構(gòu)不同
Ubuntu 是安裝在 win10 臺(tái)式機(jī)上的虛擬機(jī)中,所使用的硬件應(yīng)該為臺(tái)式機(jī)的硬件(處理器等);而臺(tái)式機(jī)的硬件是英特爾的 X86 架構(gòu)的處理器。
樹莓派使用的硬件平臺(tái),是一個(gè) ARM 架構(gòu)的芯片,具體可以參考圖片:
gcc 版本不同,在剛開始操作的時(shí)候,也詳細(xì)的列出了當(dāng)前程序使用的環(huán)境
Ubuntu14.04 中 gcc ?版本為:4.8.2
樹莓派中 gcc 版本為:8.3.0
??目前能想到的差異就這么多,其他的暫時(shí)還不知道,難道這個(gè)就是運(yùn)行在 X86 平臺(tái)和 ARM 平臺(tái)的區(qū)別之一?更多的更深入的研究還有待后續(xù)學(xué)習(xí)研究才能知道。今天的討論就到這里為止吧!
總結(jié)
在 X86 架構(gòu)平臺(tái)下,外小內(nèi)大效率較高;
由于參考的規(guī)范手冊(cè),可能是用于服務(wù)器開發(fā),而服務(wù)器仍然是 X86 架構(gòu)的處理器居多,因此 for 循環(huán)的多重循環(huán)規(guī)則較適用;
需要考慮在嵌入式等 ARM 平臺(tái)下,此規(guī)則是否同樣適用,是否還有其他應(yīng)用場(chǎng)景限制等?歡迎私信/加我好友一起討論~
推薦閱讀:
專輯|Linux文章匯總
專輯|程序人生
專輯|C語(yǔ)言
我的知識(shí)小密圈
總結(jié)
以上是生活随笔為你收集整理的多重 for 循环,如何提高效率?的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Administration inter
- 下一篇: Servlet面试题汇总