剑指offer——数组中只出现一次的数字

1、一个数字出现一次,其他数字出现两次

两个相同的数异或为0,所以将数组里的所有数依次异或,得到的结果就是只出现一次的数。

#include <iostream>
using namespace std;
int main()
{
    int a[]={3,6,2,3,2,5,5};
    int num=0;
    for(int i=0;i<7;i++)
    {
        num^=a[i];
    }
    cout<<num<<endl;
    return 0;
}

 

2、一个数字出现一次,其他数字出现N次

通过观察法,发现如果数字出现了n次,那么每一bit位之和可以被n整除。

#include <iostream>
#include <string>
using namespace std;
int FindNumber(int a[], int n, int m)
{
  int bits[32];
  int i, j;
  // 累加数组中所有数字的二进制位
  memset(bits, 0, 32 * sizeof(int));
  for (i = 0; i < n; i++)
    for (j = 0; j < 32; j++)
      bits[j] += ((a[i] >> j) & 1);
  // 如果某位上的结果不能被整除,则肯定目标数字在这一位上为
  int result = 0;
  for (j = 0; j < 32; j++)
    if (bits[j] % m != 0)
      result += (1 << j);
  return result;
}
int main()
{
  int a[] = {2, 3, 1, 2, 3, 4, 1, 2, 3, 1};
  //3代表其他数字出现3次
  cout<<FindNumber(a, 10, 3)<<endl;
  return 0;
}

 

3、两个数字出现一次,其他数字出现两次

和1的原理差不多,先是分别异或,得到结果,肯定不为0。找到结果1所在的位置x,将原数组分为两部分,第一部分是x为1的数的集合,第二部分是x为0的数的集合。然后分别对这两个数组异或,得到这两个出现一次的数。

#include <iostream>
#include <string>
using namespace std;

unsigned int FindFirstBitIs1(int num)
{
    int indexBit=0;
    while(((num&1)==0)&&(indexBit<8*sizeof(int)))
    {
        num=num>>1;
        ++indexBit;
    }
    return indexBit;
}

bool IsBit1(int num,unsigned int indexBit)
{
    num=num>>indexBit;
    return (num&1);
}

void FindNumsAppearance(int data[],int length,int *num1,int *num2)
{
    if (data==NULL||length<2)
    {
        return;
    }
    int resultExclusiveOR=0;
    for (int i=0;i<length;i++)
    {
        resultExclusiveOR^=data[i];
    }
    unsigned int indexof1=FindFirstBitIs1(resultExclusiveOR);
    *num1=*num2=0;
    for (int j=0;j<length;j++)
    {
        if (IsBit1(data[j],indexof1))
        {
            *num1^=data[j];
        }
        else
        {
            *num2^=data[j];
        }
    }
}

int main()
{
    int a[]={4,3,6,3,2,5,5};
    int temp1,temp2;
    FindNumsAppearance(a,7,&temp1,&temp2);
    cout<<temp1<<"\t"<<temp2<<endl;
    return 0;
}

参考:

http://blog.csdn.net/morewindows/article/details/12684497

posted @ 2014-09-09 10:05  啵啵那个臭  阅读(116)  评论(0编辑  收藏  举报