1 快速排序的实现

 

思想:指定划分元素,如key=data[l],然后i先由左至右遍历数组并同时判断与key的大小,比key大则停止遍历,再j从右向左开始遍历数组并同时判断与key的大小,比key小则停止,两趟比较后,比较i与j的大小,i>j则不交换两数,否则交换data[i]与data[j]。当i>j时交换data[j]与data[l],最后返回key的位置j。这是一次划分,再分别从l -- j-1 和 j+1 -- h重复上面的划分过程.

具体代码如下:

 

void exch(int &a, int &b)  //交换两个元素
{
	int temp = a;
	a = b;	
	b = temp;
}


//划分位置
int partion(int *data, int l, int h)
{
	int key = data[l];
	int i=l, j=h+1;
	while(1)
	{
		while(data[++i]<key)  if(i==h) break;
		while(data[--j]>key)  if(j==l) break;
		if(i>j)	break;
		exch(data[i], data[j]);
	}
	exch(data[l], data[j]);
	return j;
}
//快速排序
void qsort(int *data, int l, int h)
{
	if(l>h) 	return ;
	int pivot=partion(data, l, h);
	qsort(data, l, pivot-1);
	qsort(data, pivot+1, h);
}

 

 

2.优化快速排序,使其实划分位置为随机的,即key的值数组中的随机数字

 

 

int Less(int a, int b)
{	return ((a<b)?1:0); }
void exch(int &a, int &b)
{	int temp=a; a=b; b=temp; }
int partion(int *data, int l, int h)
{
	srand((unsigned)time(NULL));
	exch(data[l+rand()%(h-l+1)], data[l]); 
	int i=l, j=h+1;
	int pivot=data[l];
	while(1)
	{	
		while(Less(data[++i], pivot)) if(i==h) break;
		while(!Less(data[--j], pivot)) if(j==l) break;
		if(i>=j)	break;
		exch(data[i], data[j]);
	}
	exch(data[l], data[j]);	
	return j;
}

void sort(int *data, int l, int h)
{
	if(l>=h) return ;
	int pivot=partion(data, l, h);
	sort(data, l, pivot-1);
	sort(data, pivot+1, h);
}

 


3 使用快速排序的思想解决划分奇偶数的问题,是数组中奇数在前,偶数在后

思路:就是在划分数组的过程中,将划分起始位置元素除以0,能整除则停止由左向右的遍历,开始由右向左遍历,步骤与上述一样

代码如下

 

//使用快速排序的思想解决划分奇偶数问题
void pivot_event(int *data, int l, int h, bool (*pfun)(int))  //pfun函数指针指向isEvent函数
{
	int key=data[l];
	int i=l, j=h+1;
	while(1)
	{
		while(!pfun(data[++i])) if(i==h) break;
		while(pfun(data[--j]))  if(j==l) break;
		if(i>j) break;
		exch(data[i], data[j]);
	}
	exch(data[l], data[j]);
}

 

 

4 使用快速排序的思想解觉输出数组中第k个大的数,或者第k个小的数

思路与快速排序的思想一模一样,在一次划分后的位置j,如果比k-1大,则在l -- j-1处继续划分数组;如果比k-1小,则在j+1 -- h处划分数组,直到j==k位置时停止划分数组
代码如下:
//使用快排思想找到数组的第k大的数
int pivot_k(int *data, int l, int k, int h, bool (*pfun)(int, int)) //pfun函数指针指向isLess函数
{
	int key;
	key = data[l];
	int i=l, j=h+1;
	while(1)
	{
		while(isLess(data[++i], key)) if(i==h)  break;
		while(!isLess(data[--j], key)) if(j==l) break;
		if(i>j)	break;
		exch(data[i], data[j]);
	}
	exch(data[l], data[j]);
	if(j<k-1)
		pivot_k(data, j+1, k, h, isLess);
	else if(j>k-1)
		pivot_k(data, l, k, j-1, isLess);
	else
		return j;
}