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

經典算法:三種交換兩個整數的方法與底層原理深度解析

     編輯:PHP 相關知識

經典算法:三種交換兩個整數的方法與底層原理深度解析

交換兩個變量值是程序設計入門必學操作,但不同實現方式在性能、適用場景、副作用上差異巨大。本文對比臨時變量法、算術運算法、異或運算法三種經典寫法,從 CPU 指令、溢出風險、編譯器優化角度深度剖析。

方法一:臨時變量法(標準庫推薦)

void swap_temp(int *a, int *b) {
    int tmp = *a;
    *a = *b;
    *b = tmp;
}
  • 優點:可讀性最強、無副作用、支持任意類型(結構體、浮點數、指針)。
  • 性能:現代編譯器(GCC/Clang -O2)會優化為 xchg 指令或寄存器重命名,零內存訪問開銷。
  • 缺點:額外棧內存(可忽略)。

方法二:算術運算法(無臨時變量)

void swap_arith(int *a, int *b) {
    *a = *a + *b;
    *b = *a - *b;
    *a = *a - *b;
}
  • 致命缺陷:整數溢出導致未定義行為(UB)。當 *a + *b > INT_MAX 時,有符號整數溢出在 C/C++ 中屬 UB,編譯器可假設不發生而優化掉邏輯。
  • 浮點數不可用:精度丟失導致結果錯誤。
  • 同地址失效:若 a == b,會將值歸零。

方法三:異或運算法(位運算技巧)

void swap_xor(int *a, int *b) {
    *a = *a ^ *b;
    *b = *b ^ *a;
    *a = *a ^ *b;
}
  • 優點:無溢出風險、無臨時變量、適用於整數類型。
  • 缺點:
    1. 同地址歸零:a == b 時 *a ^= *a → 0。
    2. 現代 CPU 慢:三條依賴鏈指令,無法並行,比 xchg/臨時變量法慢。
    3. 不可用於浮點/指針:違反嚴格別名規則,屬 UB。

性能實測(x86-64, GCC 12 -O3)

方法指令數吞吐周期備註
tmp 變量3 (mov/mov/mov)1寄存器重命名,最快
XCHG 指令13鎖總線,多核下較慢
異或3 (xor/xor/xor)3依賴鏈長,無法流水線
算術3 (add/sub/sub)3同異或,且有溢出風險

最佳實踐建議

  1. 生產代碼永遠使用臨時變量法,或直接調用 std::swap/std::ranges::swap(C++20),編譯器會自動選擇最優實現。
  2. 嵌入式極度受限寄存器場景(如 8 位單片機)可考慮異或法,但必須加入 if (a != b) 守衛。
  3. 面試考察點:考官通常想聽到「溢出 UB」、「同地址歸零」、「現代編譯器優化」、「可讀性優先」等關鍵詞。

GitHub 完整代碼:SwapFunction。理解底層原理,才能在權衡性能與安全時做出正確工程決策。

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