基数排序和计数排序

基数排序,计数排序是常用的几种非比较排序,之前涉及到的排序方式基本都是基于比较的,复杂度最优的情况是O(nlogn),而非比较排序可以实现线性时间完成排序。但是相应的空间复杂度会有所增加。

桶排序(计数排序) :对于序列中的每一个元素,计算得到小于该元素的元素个数,从而确定了该元素在最终输出元素的位置。计数排序有一个非常重要的地方就是:假定数据的范围是在某个区间内,如果数据的大小相差非常大的话,那么计数排序是不适用的。比如三个数1,11111111,222222222222,那么在计数排序中开辟的空间消耗和时间消耗是非常不值得的。

代码如下:

public class BucketSort{
	public static void buckerSort(int []arr){
		if (arr==null||arr.length==0) {
			return ;
		}
		int max=Integer.MIN_VALUE;
		for (int i=0; i0){
				arr[i++]=j;
			}
		}
	}
}

基数排序比较复杂,基数排序最初是用在打孔卡片制表机上的一种排序算法,由Herman Hollerith发明,也就是IBM的创始人。基数排序从最低为开始来排序的,从低位到高位,按位排序,按位排序必须是稳定的。

代码:

class RadixSort{
	public static void radixSort(int []arr){
		if (arr==null||arr.length==0) {
			return ;
		}
		radixSort(arr,0,arr.length-1,maxbits(arr));
	}
	public static int maxbits(int []arr){
		int max=Integer.MIN_VALUE;
		for (int i=0; i=begin; i--) {
				j=getDigit(arr[i],d);
				bucket[count[j]-1]=arr[i];
				count[j--];
			}
			for (i=begin,j=0; i

计数排序的一种应用:求数组排序后相邻两个数的最大差值。这里将数字放入桶中,以大于0,小于100的数为例。我们可以根据题目需要分出10个桶,第一个桶放0~9范围内的数,第二个10~19范围内的数,......依次类推。同一个桶内的数字之差一定小于两个桶之间的差。那么又因为数组是经过排序的。所以最大差值一定出现在(前一个桶的最大值与其之后的桶的最小值之差)之间。我们用一个大小为10个数组存这些值之间的差。然后找出最大值即可。

public class MaxGap {
	public static int maxGap(int []nums){
		if (nums==null||nums.length<2) {
			return 0;
		}
		int len=nums.length;
		int min=Integer.MAX_VALUE;
		int max=Integer.MIN_VALUE;
		for (int i = 0; i < len; i++) {
			//求出数组中的最大值与最小值。
			min=Math.min(min, nums[i]);
			max=Math.max(max, nums[i]);
		}
		if (max==min) {
			return 0;
		}
		//默认为false
		boolean hasNum[]=new boolean[len+1];
		int []maxs=new int [len+1];
		int []mins=new int [len+1];
		int bid=0;
		for (int i = 0; i < len; i++) {
			//得出同一个桶内的最大值最小值即可
			bid=bucket(nums[i],len,min,max);
			maxs[bid]=hasNum[bid]?Math.max(maxs[bid], nums[i]):nums[i];
			mins[bid]=hasNum[bid]?Math.min(mins[bid], nums[i]):nums[i];
		}
		int res=0;
		int lastMax=maxs[0];
		int i=1;
		//最大差值是前一个桶的最大值与当前桶的最小值之间的差
		for (; i < len; i++) {
			if (hasNum[i]) {
				res=Math.max(res, mins[i]-lastMax);
				lastMax=maxs[i];
			}
		}
		return res;	
	}
	//根据值大小判断存储的位置
	private static int bucket(long num, long len, long min, long max) {
		return (int) ((num-min)*len/(max-min));
	}
	
}


你可能感兴趣的:(刷题)