给定一个长为N的数组,数组中有一出现大于N/2次的数,要求快速找到该数。
Thinking:
暴力的方法可以对数组进行排序,然后依次统计数字出现的次数,最后再找到出现大于N/2次的数字,但这样效率低,时间复杂度可以达到O(N*logN + N);
或者可以先进行排序后,数组第N/2位置上的数字必定是所求数字,但时间复杂度受限于排序算法;
因此我们希望有不用排序的简单方法,即每次删除两个不同的数字,因为所求的数字大于N/2个,所以重复操作后最后的数字必为所求数字。
Code:
void Find(int *a, int n)
{
int ans;
int ntimes, i;
for (i = ntimes = 0; i < n; i++)
{
if (ntimes == 0) //重置ans
{
ans = a[i];
ntimes = 0;
}
else
{
if (ans != a[i])//数字不同,删除
ntimes--;
else //数字相同,保留
ntimes++;
}
}
cout << "The answer number is " << ans << endl;
}