您的位置:首页 > 其它

描述一个运行时间为Θ(nlgn)的算法,给定n个整数的集合S和另一个整数x,该算法能确定S中是否存在两个其和刚好为x的元素

2013-12-14 16:24 836 查看
算法思路:

首先对S[1...n]进行非降序排序,然后设置两个指向标i=1,j=n,执行下面的操作:

S[i] + S[j] = X,  返回true

    < X,   i = i+1

     > X,   j = j-1

   如果 i>j 返回false

#include <iostream>
#include <ctime>
#include <limits>

using namespace std;

void merge(int *a,int low,int mid,int high)//哨兵法 归并排序
{
int Ln=mid-low+1;
int Rn=high-mid;

int *La=new int[Ln+1];
int *Ra=new int[Rn+1];

for(int i=0;i<Ln;++i){
La[i]=a[low+i];
}
for(int j=0;j<Rn;++j){
Ra[j]=a[mid+j+1];
}
La[Ln]=numeric_limits<int>::max();
Ra[Rn]=numeric_limits<int>::max();

int m=0,n=0;
for(int k=low;k<=high;++k){
if(La[m]<=Ra
){
a[k]=La[m];
++m;
}else{
a[k]=Ra
;
++n;
}
}
}

void merge_sort(int * a,int low,int high)//O(n*lgn)
{
if(low<high){
int mid=(low+high)>>1;
merge_sort(a,low,mid);
merge_sort(a,mid+1,high);
merge(a,low,mid,high);
}
}

bool sum_to_x(int *a,int low,int high,int x)//求序列S中是否存在两个数之和为X,O(n)
{
int i=low,j=high;
while (i<j){
if(x==(a[i]+a[j])){
return true;
}else if(x<(a[i]+a[j])){
--j;
}else{
++i;
}
}
return false;

}

int main()
{
srand(time(NULL));
int count;
while ((count=rand()%20)<3);
int *a=new int[count];

for(int i=0;i<count;++i){
a[i]=rand()%35;
cout<<a[i]<<" ";
}
cout<<endl;

merge_sort(a,0,count-1);

for(int i=0;i<count;++i){
cout<<a[i]<<" ";
}
cout<<endl;
int x=rand()%100;
bool flag=sum_to_x(a,0,count-1,x);

cout<<x<<" is in S ? "<<boolalpha<<flag<<endl;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐