题目:
数组中有一个数字出现的次数超过数组长度的一半,找出这个数字。
思路:
1、基于Partition函数的O(n)的解法(找到下标为n/2的数)。
2、根据数组特点找出O(n)的算法。
代码:
#include<iostream>
using namespace std;
//功能:求数组中出现次数超过一半的数字
//思路1:利用快速排序可以求出第k大的数,如果存在要求的数,那么排序后他的下标一定在n/2
int Partition(int *numbers , int begin , int end)
{
if(numbers == NULL || begin >= end)
return begin;
int x = numbers[begin];//以第一个数字为枢轴
int j = begin;
for(int i = begin + 1 ; i <= end ; i++)
{
if(numbers[i] < x)
{
j++;
swap(numbers[j] , numbers[i]);
}
}
swap(numbers[begin] , numbers[j]);
return j;
}
int MoreThanHalfNumHHT(int *numbers , int length)
{
if(numbers == NULL || length <= 0)
return -1;
int middle = length >> 1;//length/2
int index = Partition(numbers , 0 , length - 1);
while(middle != index)
{
if(index > middle)
{
index = Partition(numbers , 0 , index - 1);
}
else
{
index = Partition(numbers , index + 1 , length - 1);
}
}
return numbers[middle];
}
int MoreThanHalfNum(int *numbers , int length)
{
if(numbers == NULL || length <= 0)
return -1;
int result = numbers[0] ;
int times = 1;
for(int i = 1 ; i < length ; i++)
{
if(times == 0)
{
result = numbers[i];
times = 1;
}
else
if(numbers[i] == result)
times++;
else
times--;
}
return result;
}
int main()
{
int numbers[] = {1,2,3,4,5,6,2,2,2,2,2,2};
int length = sizeof(numbers) / sizeof(*numbers);
cout<<MoreThanHalfNum(numbers , length)<<endl;
cout<<MoreThanHalfNumHHT(numbers , length)<<endl;
}