线性时间选择算法——源码(正确运行哦)

#include <iostream>
#include <ctime>
using namespace std;
// const int len = 100; 
// int a[len]; //在调试时,为了能够关注到数组a中的变化,可将其声明为全局变量,同时,不能和函数内的局部变量同名,否则仍然看不到内容。
//冒泡排序   
template <class Type>  
void bubble_Sort(Type a[],int p,int r);
//************************************
// Method:    partition  在arr[low:high]中以x为枢轴所确定的位置
// FullName:  partition
// Access:    public 
// Returns:   int
// Qualifier:
// Parameter: Type arr[]
// Parameter: int low
// Parameter: int high
// Parameter: Type x
//************************************
template <class Type>  
int partition(Type arr[],int low,int high,Type x)  
{  //注意这个函数不要用《算法分析与设计》上的思想来写,最好用《数据结构》上的来。
	Type temp = arr[low];
	while (low < high)
	{
		while (low<high && arr[high]>=x)--high;
		arr[low] = arr[high];
		while (low<high && arr[low]<=x)++low;
		arr[high] = arr[low];
	}
	arr[low] = temp;
	return low;
}  

//************************************
// Method:    partition  在arr[low:high]中以arr[low]为枢轴所确定的位置
// FullName:  partition
// Access:    public 
// Returns:   int
// Qualifier:
// Parameter: Type arr[]
// Parameter: int low
// Parameter: int high
//************************************
template <class Type>
int partition(Type arr[], int low, int high)
{
	int i = low;
	int j = high + 1;
	Type x = arr[low];
	while (true)
	{
		while (arr[++i]<x);
		while (arr[--j]>x);
		if (i>=j)
			break;
		swap(arr[i], arr[j]);
	}
	arr[low] = arr[j];
	arr[j] = x;
	return j;
}

//************************************
// Method:    partition_2 思想:显然元素x是在arr中的,故找到它所在位置,并与arr[low]互换位置
//                        就可看做是以arr[low]为枢轴来划分了
// FullName:  partition_2
// Access:    public 
// Returns:   int
// Qualifier:
// Parameter: Type arr[]
// Parameter: int low
// Parameter: int high
// Parameter: Type x
//************************************
template <class Type>  
int partition_2(Type arr[],int low,int high,Type x)
{
	for (int i=low; i<high; ++i)
	{
		if (arr[i]==x)
		{
			swap(arr[low], arr[i]);
			break;
		}
	}
	return partition(arr, low, high); //此时可以利用arr[low]为枢轴来划分
}

template <class Type>
int compare(const void * p, const void *q)
{
	return *(Type*)p - *(Type*)q;
}
//************************************
// Method:    select_my  在数组arr[low:high]中选择第k小的元素
// FullName:  select_my
// Access:    public 
// Returns:   Type
// Qualifier:
// Parameter: Type arr[]
// Parameter: int low
// Parameter: int high
// Parameter: int k
//************************************
template<class Type>
Type select_my(Type arr[], int low, int high, int k)
{
	if (high - low < 75)
	{//此时使得当元素个数小于75时,select具有排序功能
	//	qsort(arr, high - low +1, sizeof(Type),compare<Type>); //这里的compare<Type>尤其要注意!!模板函数的特化,深刻理解Type是类型参数
		bubble_Sort(arr, low, high);
		return arr[low+k-1];
	}
	for (int i=0;i<=(high-low-4)/5; ++i)
	{
	//	select_my(arr, low+5*i, low+5*i+4, 3); //此处也可以用select来排序,因为元素个数小于75
		bubble_Sort(arr, low+5*i, low+5*i+4);
		swap(arr[low+5*i+2], arr[low+i]);

		cout <<"中位数:" << arr[low+i] << ' ';
	}
	cout << endl;

	Type x ;
	if ((low+(high-low-4)/5 - low +1)%2==0)
		x = select_my(arr, low, low+(high-low-4)/5, (high-low-4)/10+1);
	else
		x = select_my(arr, low, low+(high-low-4)/5, (high-low-4)/10);
	cout << "中位数的中位数X=" << x << endl;
	int location = partition(arr, low, high,x);  //int location = partition_2(arr, low, high,x); //success

	cout <<"以中位数的中位数为基准来划分,位置为" <<location << endl;

	int j = location-low+1;
	if (k <= j)
		return select_my(arr,low,location, k);
	else
		return select_my(arr, location+1, high, k-j);
}

//冒泡排序   
template <class Type>  
void bubble_Sort(Type a[],int p,int r)  
{
	bool exchange;    
	for(int i=0; i<=r-p+1;i++)    
	{
		exchange = false ;    
		for(int j=p; j<r-i; j++)    
		{
			if(a[j]>a[j+1])    
			{
				swap(a[j], a[j+1]);   
				exchange = true; 
			}
		}     
		//如果这次遍历没有元素的交换,那么排序结束      
		if(false == exchange)    
		{ 
			break ;    
		}  
	}  
}   
int main()
{
	
    const int len = 100; 
	int a[len]; //在调试时,为了能够关注到数组a中的变化,可将其声明为全局变量,同时,不能和函数内的局部变量同名,否则仍然看不到内容。
	cout << "起初数组中的元素为:" << endl;
	for (int i=0; i<len; ++i)
	{
		a[i] = len - i;
		cout << a[i] << ' ';
	}
	cout << endl;
	int k = 48;
	cout <<"第"<< k << "小的元素为:"<< select_my(a, 0, len-1, k) << endl;
//	qsort(arr, sizeof(arr)/sizeof(int), sizeof(int), compare<int>); //success
	cout << "此时数组中的元素为:"<< endl;
	for (int i=0; i<len; ++i)
	{
		cout << "a[" <<i<< "]:"<<a[i] << ' ';
	}
	return 0;
}


 

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值