在很多时候, 我们需要交换两个数字, 普遍的代码如下
int temp = a; a = b; b = temp;
显然的, 这种做法需要第三个变量来存储被交换两数其中之一
那还有没有其他方法呢?
当然有, 代码如下
a ^= b; b ^= a; a ^= b;
这种方法是可行的, 但问题是, 它为什么可行呢?
1. 异或
异或是一种在二进制下的操作, 其规则为: 相同得0, 否则得1
如: 1010 ^ 1001 = 0011
如果你多举几个例子, 你会发现, 异或相当于二进制下的不进位加法
2. 回归主题
假设我们要交换的数字a, b分别为4 和 6, 那么
a ^= b -> a = 4 ^ 6 -> a = 100 ^ 110 -> a = 010 (即 2)
b ^= a -> b = 6 ^ 2 -> b = 110 ^ 010 -> b = 100 (即 4)
a ^= b -> a = 2 ^ 8 -> a = 010 ^ 100 -> a = 110 (即 6)
想要下一步深挖, 我们得要先引出两个定理
(a ^ b) ^ b = a
a ^ b = b ^ a
再回头来看上面的代码, 将其展开为
a = a ^ b;
b = b ^ a;
a = a ^ b;
a 最终为 (a ^ b) ^ (b ^ (a ^ b))
先处理后半部分, 将其转换为((a ^ b) ^ b), 也就是a
再来看前半部分, (a ^ b) ^ a, 也就是b
b最终为b ^ (a ^ b), 很明显的看出来结果就是a
这样一来, 便优雅的完成了两数的交换
Algorithm is fantastic that it can take you in to fantast