异或交换可三步完成两整数交换且不依赖临时变量,基于自反性、恒等性、交换律和结合律;以a=5、b=9为例,经a=a^b、b=a^b、a=a^b后实现值互换,但仅适用于整型且禁止同变量操作。
可以用异或(^)运算三步完成两个整数的交换,不依赖临时变量。核心在于异或的数学性质:自反性(
a ^ a = 0
)、恒等性(
a ^ 0 = a
)和可结合性,使得值能被“暂存”在原变量中并逐步还原。
异或交换的三步执行过程
以
a = 5
、
b = 9
为例(二进制:a=0101,b=1001):
第一步:a = a ^ b
→ a 变为 5 ^ 9 = 12(1100),b 仍为 9(1001)
第二步:b = a ^ b
→ b = 12 ^ 9 = (0101 ^ 1001) ^ 1001 = 0101 = 5(原 a 值)
第三步:a = a ^ b
→ a = 12 ^ 5 = (0101 ^ 1001) ^ 0101 = 1001 = 9(原 b 值)
底层逻辑的关键性质支撑
整个过程成立,完全依赖以下四条异或代数规则:
a ^ a = 0
—— 同值抵消,是“清零”和“还原”的基础
a ^ 0 = a
—— 零值穿透,保障中间结果不被污染
a ^ b = b ^ a
—— 交换律,允许操作顺序灵活调整
(a ^ b) ^ c = a ^ (b ^ c)
—— 结合律,使多步推导合法化
第二步本质是:
b = (a ^ b) ^ b = a ^ (b ^ b) = a ^ 0 = a
;第三步同理:
a = (a ^ b) ^ a = b ^ (a ^ a) = b ^ 0 = b
。
实战注意事项与限制
该技巧虽精巧,但需警惕实际使用中的边界问题:
仅适用于
整型变量
(char/short/int/long),浮点数、结构体、指针不可直接使用
若
a 和 b 是同一变量(如 swap(&x, &x) 或宏展开时别名冲突)
,第一步后 a 变 0,后续全为 0,导致数据丢失
现代编译器对临时变量交换已高度优化,异或写法
可读性差、调试困难、无性能优势
,生产环境不推荐
加减法交换(a=a+b; b=a−b; a=a−b)有溢出风险,异或无此问题,但仅限于整数范围安全场景
代码验证示例(C语言)
可直接编译运行验证逻辑:
#include
int main() {
int a = 5, b = 9;
printf("交换前: a = %d, b = %d\n", a, b);
a = a ^ b;
b = a ^ b;
a = a ^ b;
printf("交换后: a = %d, b = %d\n", a, b); // 输出:a = 9, b = 5
return 0;
} 