异或运算,两个数一样异或结果为0,不一样则为1。
所以如果一个数组中有两个只出现一次的数字,那么这两个数一定二进制中有一位为1。比如说a的二进制有一位是1,b的二进制那一位是0,所以按这一位来分组。
首先把所有数异或,得到两个数不同的那几位的二进制,我们称为tmp。
然后遍历数组,和tmp相同的分为一组,和tmp不同的为一组。这样刚好就给两个只出现过一次的数字分开了,并且也把出现两次的数字也分到一组了(因为出现两次
#include<iostream>
using namespace std;
const int N = 1010;
int a[N], res[N];
int n;
void findNumAppearOnce(int* arr, int& res1, int& res2) {
int tmp = arr[0];
for (int i = 1; i < n; i++) {
tmp ^= arr[i];
}
int k = 1;
while ((tmp & k) == 0) k <<= 1;
for (int i = 0; i < n; i++) {
if (a[i] & k) res1 ^= arr[i];
else res2 ^= arr[i];
}
}
int main() {
cin >> n;
for (int i = 0; i < n; i++) {
cin >> a[i];
}
int res1 = 0, res2 = 0;
findNumAppearOnce(a, res1, res2);
cout << res1 << " " << res2;
return 0;
}
=> 二进制相同 => &tmp一定相同)。

京公网安备 11010502036488号