什么是異或運算?就是不一樣的位得1,一樣的位得0。
交換兩個數的值可以有這騷操作
#include <stdio.h>
int main()
{
int a = 1;
int b = 2;
a^=b^=a^=b;
printf("%d %d",a,b);
return 0;
}
它是如何做到的呢?
先來看這樣一個例子:
#include <stdio.h>
int main()
{
int a = 1;
int b = 2;
a = a + b;
b = a - b;
a = a - b;
printf("%d %d",a,b);
return 0;
}
原理就是相加后減己得他。
再來看異或交換如何做到的
- 首先明確一點,異或的位運算各位之間不會相互干擾,所以單獨拿出一位來研究就行了。
*先看兩數相同的情況,即都為1或都為0,異或運算完的值為零,分別與0異或運算得他本身。- 兩數不相同,一個1一個0的話。異或運算完是1,0與1異或得另一個數1,1與1異或得另一個數0。
- 因為每一位都是如此,所以兩個任意正整數都可以如此交換
- 與剛剛上邊加減法交換的例子有什么關系嗎?我們加兩條新規定
- 因為不存在進位所以我們定義1+1=0。
- 定義1與0的減法只能大減小。
- 再看上邊的例子是不是就明白了。
效率如何
#include <stdio.h>
#include <time.h>
int main()
{
int n=2000000000;
while(n--){
int a = 12345678;
int b = 23456789;
// int t=a;
// a=b;
// b=t;
a^=b^=a^=b;
}
printf("%f\n",(double)clock()/CLOCKS_PER_SEC);
return 0;
}
加入第三個變量快一點點,以上數據分別為平均10s和平均12s。
那么問題來了含有負數的運算為什么也適用呢?
下次研究一下反碼補碼
參考《算法競賽入門經典(第二版)》P9最下邊小字。