异或运算的简单应用

问题1:不使用临时变量,实现两个整型变量 x, y 值的交换。

以下为 C++ 实现代码:

 1 /**************************************************************
 2 author : 林秋伟
 3 time   : 2013-10-27
 4 **************************************************************/
 5 #include <iostream>
 6 using namespace std;
 7 
 8 void swap(int &x, int &y){
 9     x^=y; y^=x; x^=y; //使用异或运算交换x与y的值
10 }
11 
12 int main(){
13     int x, y;
14     while(cin>>x>>y){
15         swap(x, y);
16         cout<<x<<" "<<y<<endl;
17     }
18     return 0;
19 }

问题2:大小为 n=2*k+1 (k≥0) 的整型数组 a, 其中 x 只出现了一次,而其它的数字均出现了两次,要求在 O(n) 时间,O(1) 空间找出 x.

思路:利用 u^0=u, u^v=v^u, u^u=0 的性质可知,a[0]^a[1]^···^a[n-1]=x.

以下是 C++ 实现代码:

 1 /**************************************************************
 2 author : 林秋伟
 3 time   : 2013-10-27
 4 **************************************************************/
 5 #include <iostream>
 6 using namespace std;
 7 
 8 int find(int num[], int n){
 9     int x=0;
10     for(int i=0; i<n; i++) x^=num[i];
11     return x;
12 }
13 
14 int main(){
15     int n, a[100005];
16     while(cin>>n){
17         for(int i=0; i<n; i++) cin>>a[i];
18         int x=find(a, n);
19         cout<<x<<endl;
20     }
21     return 0;
22 }

问题3:大小为 n=2*k (k≥1) 的整型数组,其中 x, y (x≠y) 只出现了一次,而其它的数字均出现了两次,要求在 O(n) 时间,O(1) 空间找出 x, y.

思路:利用 u^0=u, u^v=v^u, u^u=0 的性质可知,a[0]^a[1]^···^a[n-1]=x^y. 由于 x≠y, 所以 x^y≠0, 即 x^y 的二进制表示中至少有一位为 1, 不妨记该位为 pos, 则可知 x, y 在该位上一个为 0, 一个为 1. 可根据这点将数组分成两组,然后分组进行异或运算,则所得即为 x, y.

以下为 C++ 实现代码:

 1 /**************************************************************
 2 author : 林秋伟
 3 time   : 2013-10-27
 4 **************************************************************/
 5 #include <iostream>
 6 using namespace std;
 7 
 8 int one(int val){  //返回val二进制表示中首个为1的位置
 9     int pos=1;
10     while(!(val&1)){
11         val>>=1;
12         pos++;
13     }
14     return pos;
15 }
16 
17 bool judge(int val, int pos){  //判断val二进制表示中第pos位是否为1
18     val>>=(pos-1);
19     return val&1;
20 }
21 
22 void find(int num[], int n, int &x, int &y){
23     int temp=0, i;
24     for(i=0; i<n; i++) temp^=num[i];
25     int pos=one(temp);
26     x=y=0;
27     for(i=0; i<n; i++){
28         if(judge(num[i], pos)) x^=num[i];
29         else y^=num[i];
30     }
31 }
32 
33 int main(){
34     int n, a[100005], x, y;
35     while(cin>>n){
36         for(int i=0; i<n; i++) cin>>a[i];
37         find(a, n, x, y);
38         cout<<x<<" "<<y<<endl;
39     }
40     return 0;
41 }

 

posted on 2013-10-27 22:43  林秋伟  阅读(158)  评论(0编辑  收藏  举报

导航