分治算法三(随机化快速排序)

1、快速排序对于输入数据的顺序比较敏感。主要在于每次划分对主元的选择。基本的快速排序选取第一个元素作为主元。这样在数组已经有序的情况下,每次划分将得到最坏的结果。这个时候,时间复杂度将会退化到O(n^2)。
2、一种比较常见的优化方法是随机化算法,即随机选取一个元素作为主元。这种情况下虽然最坏情况仍然是O(n^2),但最坏情况不再依赖于输入数据,而是取决于随机函数随机数的选取。实际上,随机化快速排序得到理论最坏情况的可能性仅为1/(2^n)。所以随机化快速排序可以对于绝大多数输入数据达到O(n*logn)的期望时间复杂度。
3、随机化快速排序的唯一缺点在于,一旦输入数据中有很多的相同数据,随机化的效果将直接减弱。对于极限情况,即对于n个相同的数排序,随机化快速排序的时间复杂度将毫无疑问的降低到O(n^2)。解决方法是用一种方法进行扫描,使没有交换的情况下主元保留在原位置。


/* file: random_quick_sort					*/
/* 1、find the pivot of the Array by using 
	  random algorithm						*/
/* 2、divide the Array into two subarrays	*/
/* 3、conquer the two subarrays				*/
/* 4、the Array is sorted,when conquer ended*/

#include<stdio.h>
#include <stdlib.h>

/*=====================================
  swap:swap two numbers a and b
=======================================*/
inline void swap(int* a,int* b)
{
	int tmp;
	tmp  = *a;
	*a   = *b;
	*b   = tmp;
}
/*=====================================
  Partition:Partition the Array from start
			to end into two subarrays.
			Return the pivot of the element
			Array[start]
=======================================*/
int Partition(int* Array, int start, int end)
{
	//choose Array[start] as the pivot element 
	//divide the array into two subarrays.
	//left of the Array's elements <= Array[start]
	//right of the array's elements > Array[start]
	int pivot = start,j;
	for(j = start + 1; j <= end; j++)
		if(Array[j] <= Array[start])
		{
			pivot++;
			swap(&Array[pivot], &Array[j]);
		}
	swap(&Array[start], &Array[pivot]);
	return pivot;
}
/*=====================================
  RandomPartition:using random algorithm.partition the
				  Array into two subarrays.Return the 
				  pivot of the element Array[start] which
				  is already swaped
=======================================*/
int RandomPartition(int* Array, int start, int end)
{
	//generate the random index of the pivot
	int random_index = start + rand() % (end - start + 1);
	//swap the pivot with the random_index element
	swap(&Array[start], &Array[random_index]);
	//now random_index element act as the start element
	return Partition(Array,start,end);
}

/*=====================================
  RandomQuickSort:Sort the Array using QuickSort
				  algorithm.By partition an Array
				  into two subarrays and then 
				  conquer the two subarrays.
=======================================*/
void RandomQuickSort(int* Array, int start,int end)
{
	int pivot;
	if(start < end)
	{
		//find the pivot of the array
		pivot = RandomPartition(Array, start, end);
		//conquer the left subarray
		RandomQuickSort(Array, start, pivot - 1);
		//conquer the right subarray
		RandomQuickSort(Array, pivot + 1, end);
	}
}

void main()
{
	int n,i;

	printf("Please input the length of Array<0:exit>:\n");
	while(scanf("%d",&n),n)
	{	
		//create an arrays of length n
		int* Array = new int[n];
		//get the input integers
		printf("Please input %d integers:\n",n);
		for(i = 0; i < n; i++)
			scanf("%d",&Array[i]);
		//use QuickSort algorithom
		RandomQuickSort(Array,0,n-1);
		//print the sorted array
		printf("Sorted Array:\n");
		for(i = 0; i < n; i++)
			printf("%d ",Array[i]);
		system("pause");
		system("cls");
		//delete the array
		delete[] Array;
		printf("Please input the length of Array<0:exit>:\n");
	}
}


  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值