/**
题意:
一个整型数组里除了两个数字之外,其他的数字都出现了偶数次,
请写程序找出这两个出现一次的数字。
要求时间复杂度是O(n),空间复杂度是O(1).
解题思路:用异或操作
偶数个的异或起来为0,所以最后异或的答案等于所求两数异或和
这两个数不一样那么异或结果一定至少有一位为1。表示num1该位为1,num2该位为0。
将该位为1的数全部异或起来,得到的结果是num1。
这是因为除了num1之外,剩下的每个数(当然不包括num2)一定有偶数个。
同理将该位为0的数全部异或起来,得到的结果是num2。
*/
#include <stdio.h>
unsigned int FindFirstBitIs1(int num)
{
int indexBit = 0;
while (((num & 1) == 0) && (indexBit < 32))
{
num = num >> 1;
++ indexBit;
}
return indexBit;
}
bool IsBit1(int num, unsigned int indexBit)
{
num = num >> indexBit;
return (num & 1);
}
void FindNumsAppearOnce(int data[], int length, int &num1, int &num2)
{
if (length < 2)///即第一个和第二个数
return;
int resultExclusiveOR = 0;
for (int i = 0; i < length; ++ i)
resultExclusiveOR ^= data[i];
///找到第一位(2进制)是1的
unsigned int indexOf1 = FindFirstBitIs1(resultExclusiveOR);
num1 = num2 = 0;
for (int j = 0; j < length; ++ j)
if(IsBit1(data[j], indexOf1))///该位为1的异或起来
num1 ^= data[j];
else
num2 ^= data[j]; ///该位不为1的异或起来
}
}
int main()
{
int n,i,x,y;
int a[99999];
while(scanf("%d",&n)!=EOF)
{
for(i=0;i<n;i++)
scanf("%d",&a[i]);
FindNumsAppearOnce(a,n,x,y);
printf("%d\n",x+y);
}
return 0;
}
数组中仅出现一次的两个数-异或
最新推荐文章于 2023-03-31 22:44:58 发布