题目描述:
一个整型数组里除了两个数字之外,其他的数字都出现了两次。请写程序找出这两个只出现一次的数字。
思路:
由于两个相同的数字异或等于0,将数组中所有数字异或之后 肯定得到一个非零数,找到该数二进制位表示的第一个非零位,记位第n位,遍历数组,依次判断数组中元素的第n位是否为1,为1的分为一组,为0的分为一组,则两个只出现一次的数字肯定被分到了不同组中,将两组数分别异或,即可得到两个只出现一次的数字。
时间复杂度O(n),空间复杂度O(1)
class Solution {
public:
void FindNumsAppearOnce(vector<int> data,int* num1,int *num2) {
if (data.empty() || data.size() < 2) return;
int res = 0;
for (auto ele : data) {
res ^= ele;
}
unsigned int indexOf1 = FindFirstBitIs1(res);
*num1 = *num2 = 0;
for (auto ele : data) {
if (IsBit1(ele, indexOf1))
*num1 ^= ele;
else
*num2 ^= ele;
}
}
//找到二进制表示中第一个非0位
unsigned int FindFirstBitIs1(int num) {
int indexBit = 0;
while (((num & 1) == 0) && (indexBit < 8 * sizeof(int))) {
num >>= 1;
++indexBit;
}
return indexBit;
}
//判断数字二进制表示的第n位是否为1
bool IsBit1(int num, unsigned int indexOf1) {
num >>= indexOf1;
return (num & 1);
}
};