一、目的
1.熟悉算法设计的基本思想
2.掌握随机选择算法(rand select)的方法
3.掌握选择算法(SELECT)的方法
二、内容与设计思想
- 编写随机整数生成算法,生成S到T范围内的N个随机整数并输出;
- 编写随机选择算法和SELECT算法;
- 随机生成1e2、1e3、1e4、1e5、1e6个数,使用随机选择算法和SELECT算法找到第0.5N大的数输出,并画图描述不同情况下的运行时间差异;
- 随机生成1e6个数,使用随机选择算法和SELECT算法找到第0.2N、0.4N、0.6N、0.8N大的数输出,并画图描述不同情况下的运行时间差异;
三、使用环境
推荐使用C/C++集成编译环境。
四、实验过程
1、 写出随机选择算法的源代码
#include<bits/stdc++.h>
using namespace std;
#define MaxData 10000001
int a[MaxData]={0};
int Partition(int a[],int p,int r)
{
int x,i,j,t;
x=a[r];
i=p-1;
for (j=p;j<r;j++)
{
if (a[j]<=x)
{
i=i+1;
t=a[i];
a[i]=a[j];
a[j]=t;
}
}
t=a[i+1];
a[i+1]=a[r];
a[r]=t;
return i+1;
}
int RandomizedPartition(int a[],int p,int r)
{
int i,t;
i=rand()%(r-p)+p;
t=a[i];
a[i]=a[r];
a[r]=t;
return Partition(a,p,r);
}
int RandomizedSelect(int a[],int p,int r,int i)
{
int q,k;
if (r==p)
{
return a[p];
}
q=RandomizedPartition(a,p,r);
k=q-p+1;
if (i==k)
{
return a[q];
}
else if (i<k)
{
return RandomizedSelect(a,p,q-1,i);
}
else
{
return RandomizedSelect(a,q+1,r,i-k);
}
}
int main()
{
int i,p,r,j,X,N;
cin>>N>>i;
p=1;
r=N;
srand(time(0));
for (j=1;j<=N;j++)
{
a[j]=rand();
}
X=RandomizedSelect(a,p,r,i);
clock_t startTime,endTime;
startTime = clock();
X=RandomizedSelect(a,p,r,i);
endTime = clock();
cout << "The run time is:" <<(double)(1000*(endTime - startTime) / CLOCKS_PER_SEC) << "ms" << endl;
cout<<X;
return 0;
}
2、写出SELECT算法的源代码
#include<bits/stdc++.h>
using namespace std;
#define MaxData 1000001
int a[MaxData]={0};
int MedianArr[MaxData]={0};
void InsertionSort(int a[],int p,int r)
{
int key,i,j;
for (j=p+1;j<=r;j++)
{
key=a[j];
i=j-1;
while (i>=p&&a[i]>key)
{
a[i+1]=a[i];
i=i-1;
}
a[i+1]=key;
}
}
int FindMedian(int a[],int p,int r)
{
int i,num,remain,elem;
if (p==r)
{
return a[p];
}
for (i=p;i<r-5;i+=5)
{
InsertionSort(a,i,i+4);
num=i-p;
MedianArr[num/5]=a[i+2];
}
remain=r-i+1;
if (remain>0)
{
InsertionSort(a,i,r);
num=i-p;
MedianArr[num/5]=a[i+remain/2];
}
elem=r/5-1;
if (r%5!=0)
{
elem++;
}
if (elem==0)
{
return MedianArr[0];
}
else
{
return FindMedian(MedianArr,0,elem);
}
}
int Index(int a[],int p,int r,int median)
{
for (int i=p;i<=r;i++)
{
if (a[i]==median)
{
return i;
}
}
}
int Partition(int a[],int p,int r)
{
int x,i,j,t,median,index;
median=FindMedian(a,p,r);
index=Index(a,p,r,median);
t=a[r];
a[r]=a[index];
a[index]=t;
x=a[r];
i=p-1;
for (j=p;j<r;j++)
{
if (a[j]<=x)
{
i=i+1;
t=a[i];
a[i]=a[j];
a[j]=t;
}
}
t=a[i+1];
a[i+1]=a[r];
a[r]=t;
return i+1;
}
int Select(int a[],int p,int r,int i)
{
int k,q;
if (p==r)
{
return a[p];
}
q=Partition(a,p,r);
k=q-p+1;
if (i==k)
{
return a[q];
}
else if (i<k)
{
return Select(a,p,q-1,i);
}
else
{
return Select(a,q+1,r,i-k);
}
}
int main()
{
int p,r,i,j,N,X;
cin>>N>>i;
p=1;
r=N;
srand(time(0));
for (j=1;j<=N;j++)
{
a[j]=rand();
}
clock_t startTime,endTime;
startTime = clock();
X=Select(a,p,r,i);
endTime = clock();
cout << "The run time is:" <<(double)(1000*(endTime - startTime) / CLOCKS_PER_SEC) << "ms" << endl;
cout<<X;
return 0;
}
3、截取各个实验的实验结果
4、分别画出各个实验结果的折线图