首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

C 語言 if-else 效能測試:分支預測與編譯器優化實測

     編輯:關於C語言

實驗設計

環境:Mac Pro (i7 2.3GHz)、GCC 4.9、-O0(關閉優化)。測試 1 億次迴圈,每迴圈 10 次 if-else,比較條件為真與為假時的執行時間。

測試代碼 1:條件恆真 (b<0,b=-1)

int main() {
    int n=100000000, b=-1;
    while (n--) {
        if (b<0) b--; else b--;
        if (b<0) b--; else b--;
        // 重複 10 次
    }
    return 0;
}

測試代碼 2:條件恆假 (b>0,b=-1)

int main() {
    int n=100000000, b=-1;
    while (n--) {
        if (b>0) b--; else b--;
        if (b>0) b--; else b--;
        // 重複 10 次
    }
    return 0;
}

彙編碼分析(關鍵片段)

兩版本彙編幾乎相同,差別僅在條件跳轉指令:

  • 代碼 1:jns (Jump if Not Sign / SF=0) → 條件真時跳過 else。
  • 代碼 2:jle (Jump if Less or Equal) → 條件假時跳過 if 體。

其餘指令(subl、jmp、迴圈控制)完全一致。

執行結果

代碼 1 (條件真)  耗時:約 2.31 秒
代碼 2 (條件假)  耗時:約 2.18 秒

執行時間截圖

結論與解讀

  1. else 分支略快:在 -O0 下,編譯器生成「條件成立執行 if 體、不成立跳過」的直線碼。條件為假時直接落入 else 體(連續指令),無額外跳轉;條件為真需跳過 else 體,多一條跳轉指令。
  2. 現代 CPU 分支預測:若開啟 -O2/-O3,編譯器會將重複常數條件優化掉(死碼消除),兩版本皆極快。實際專案中分支預測器能極精準預測固定模式,差異可忽略。
  3. 最佳實務:將機率較大的情況放在 if 體,讓常見路徑無跳轉;但可讀性優先,除非經分析器證實為熱點瓶頸,否則不要為微小效能犧牲清晰度。

延伸:GCC __builtin_expect 提示分支預測

if (__builtin_expect(condition, 1)) { /* likely */ }
else { /* unlikely */ }

編譯器會將 likely 路徑安排為直線碼,unlikely 路徑放在冷碼區。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved