c++ 運算執行效率的提高技巧
阿新 • • 發佈:2018-12-01
儘量避免使用值傳遞,推薦使用const 引用來傳遞引數
臨時變數的代價。
迴圈體中的區域性變數,儘量在迴圈體內定義
複製操作與構造解構函式的代價差異。
避免過大的迴圈
cache的時間侷限性和空間侷限性
時間侷限性:如果一個儲存單元被訪問,則可能該單元會很快再次被訪問,因為存在迴圈;
空間侷限性:如果一個儲存單元被訪問,則可能該單元臨近的單元也可能很快被訪問,因為程式中大部分指令是順序儲存,
資料也一般是集中在一起的。
如果迴圈體的空間代價大於cache的容量,則不能充分利用cache了,因為cache需要與記憶體交換程式碼指令和資料。
區域性變數的效率高於靜態變數
儘量減少除法的使用
無論對於整數還是浮點數,出發都是一個運算速度很慢的指令。以下的一些簡單方法可以用來來提高效率:
- 用 if(a*n > b) 來代替 if(a>b/n) ;
- 儘量使用無符號整形變數;
- 除數使用常量有利於編譯器優化,也可以用const來修飾變數達到目的;
- 使用 x << 3 代替 x/8;
- 使用 x&7 代替 x/8;
將小粒度函式申明為行內函數(inline)
多使用建構函式初始化代替賦值初始化
建構函式與臨時變數&賦值的代價差異。
儘量減少迴圈的巢狀層數,嘗試使用多個迴圈代替
跳轉和分支執行代價高,如果可能儘量少用
- 函式呼叫需要兩次跳轉,外加棧記憶體操作;
- 儘量減少再迴圈內呼叫函式;
- 儘量使用switchcase 代替 較長的 ifelse分支;
對於優先使用 += -= 代替 + -;
而對於基本型別優先使用 + - 而不是 += -=;
如果你需要初始化一大段的記憶體,儘量使用 memset 代替賦值
++ i 代替 i++
13.
1 c = a+b; 2 d = a+b+e; 3 f = a+b+g;
優化為
1 c = a+b; 2 d = c+e; 3 f = c+g;
充分利於CPU的流水
利用CPU的流水來做平行計算,比如:
優化前
1 for (int i = 0; i < len; i++) 2 { 3 sum += a[i]; 4 }
優化後:
1 for (int i = 0; i < len; i = i + 4) 2 { 3 sum1 += a[i]; 4 sum2 += a[i + 1]; 5 sum3 += a[i + 2]; 6 sum4 += a[i + 3]; 7 } 8 sum + sum1 + sum2 + sum3 + sum4;