排序算法汇总Java

1、冒泡排序

/*冒泡排序:
1、比较相邻的元素,如果第一个比第二个大,则交换顺序;
2、对每一对相邻的元素作相同的工作,从开始第一对到结尾的最后一对,直至最大元素在数组末尾;
3、重复以上步骤,除了最后一个;
4、重复以上步骤。*/
import java.util.Scanner;

public class bubbleSort {
	public static int[] sort(int[] array) {
		if(array.length == 0) {
			return array;
		}
		int temp = 0;
		for(int i = 0; i < array.length; i ++) {
			for(int j = 0; j < array.length - i - 1; j ++) {
				if(array[j] > array[j + 1]) {
					temp = array[j + 1];
					array[j + 1] = array[j];
					array[j] = temp;
				}
			}
		}
		return array;
	}
	public static void main(String args[]) {
		Scanner sc = new Scanner(System.in);
		int n = sc.nextInt();
		int[] arr = new int[n];
		for(int i = 0; i < n ; i ++) {
			arr[i] = sc.nextInt();
		}
		for(int j = 0; j < n ; j ++) {
			System.out.print(sort(arr)[j] + ",");
		}
	}
}

2、选择排序

package paixu;
/*选择排序:
1、从无序区中选择最小值,与无序区的第一个数字交换;
2、n-1趟结束后,数组有序化。*/
public class selectionSort {
	public static int[] sort(int[] array) {
		if(array.length == 0) {
			return array;
		}
		for(int i = 0; i < array.length; i ++) {
			int minIndex = i;
			for(int j = i; j < array.length ; j ++) {
				if(array[minIndex] > array[j]) {
					int temp = array[minIndex];
					array[minIndex] = array[j];
					array[j] = temp;
				}
			}
		}
		return array;
	}
	public static void main(String args[]) {
		int[] arr = new int[] {7,1,5,9,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr)[i] + ",");
		}
	}
}

3、插入排序

package paixu;
/*插入排序:
对于未排序数据,将已排序数据从后向前扫描,找到相应位置插入。
1、第一个元素,认为已被排序;
2、从第二个元素开始从后向前扫描,将比它大的元素向后移一个位置,直到遇到比自身数值小的元素,将元素排在其后面;
3、重复步骤2。*/
public class insertionSort {
	public static int[] sort(int[] array) {
		if(array.length == 0) {
			return array;
		}
		for(int i = 0; i < array.length - 1; i ++) {
			int preIndex = i;
			int current = array[i + 1];
			while(preIndex >= 0 && current < array[preIndex]) {
				array[preIndex + 1] = array[preIndex];
				preIndex --;
			}
			array[preIndex + 1] = current;
		}
		return array;
	} 
	public static void main(String args[]) {
		int[] arr = new int[] {7,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr)[i] + ",");
		}
	}
}

4、希尔排序

package paixu;
/*希尔排序:
特殊的插入排序,间隔依次为gap=len/2,gap=len/2/2,...*/
public class shellSort {
	public static int[] sort(int[] array) {
		if(array.length == 0) {
			return array;
		}
		int len = array.length;
		int gap = len / 2;
		while(gap > 0) {
			for(int i = 0; i < len - gap; i ++) {
				int current = array[i + gap];
				int preIndex = i;
				while(preIndex >= 0 && array[preIndex] > current) {
					array[preIndex + gap] = array[preIndex];
					preIndex -= gap;
				}
				array[preIndex + gap] = current;
			}
			gap = gap >> 1;
		}
		return array;
	} 
	public static void main(String[] args) {
		int[] arr = new int[] {7,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr)[i] + ",");
		}
	}
}

5、归并排序

package paixu;

import java.util.Arrays;

/*归并排序:
将两个有序数组归并成一个有序数组
*/
public class mergeSort {
	public static int[] sort(int[] array) {
		if(array.length < 2) {
			return array;
		}
		int mid = array.length / 2;
		int[] left = Arrays.copyOfRange(array, 0, mid);
		int[] right = Arrays.copyOfRange(array, mid, array.length);
		return merge(sort(left),sort(right));
	} 
	public static int[] merge(int[] left, int[] right) {
		int[] result = new int[left.length + right.length];
		int i = 0;
		int j = 0;
		for(int index = 0; index < result.length; index ++) {
			if(i >= left.length) {//将另一边多出来的数组放到result数组中
				result[index] = right[j];
				j ++;
			}else if(j >= right.length){
				result[index] = left[i];
				i ++;
			}else if(left[i] > right[j]) {//小的数字放到result数组中
				result[index] = right[j];
				j ++;
			}else {
				result[index] = left[i];
				i ++;
			}
		}
		return result;
	}
	public static void main(String[] args) {
		int[] arr = new int[] {7,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr)[i] + ",");
		}
	}
}

6、快速排序

package paixu;

import java.util.Arrays;

/*快速排序:
冒泡排序的升级,都属于交换类排序
每一趟排序将待排序数列分为两部分,再分别对这两部分继续排序,直到数列有序。
1、从数列中挑出一个元素,作为基准值;
2、对数列进行排序,比基准值大的放在基准值的后面,比基准值大的放在基准值的前面;
3、递归的对左右子序列进行步骤2,直至各区间只有一个数。
*/
public class quickSort {
	public static int[] sort(int[] array, int start, int end) {
		if(array.length == 0 || start >= end) {
			return array;
		}
		int pivot = array[start];// 取数组的第一个元素作为基准值
		int left = start; //左标记
		int right = end;//右标记	
		while(left < right) {
			//从右向左扫描,直到遇到比基准值小的元素
			while(left < right && array[right] > pivot) {
				right --;
			}
			if(left < right) {
				array[left] = array[right];//交换右扫描第一个比基准值小的数
				left ++;//左标记右移一位
			}
			//从左向右扫描,直到遇到比基准值大的元素
			while(left < right && array[left] < pivot) {
				left ++;
			}
			if(left < right) {
				array[right] = array[left];//交换左扫描第一个比基准值大的数
				right --;//右标记左移一位
			}
		}
		array[left] = pivot;//此时left为中间位置
		sort(array, start, left - 1);//递归,左侧排序
		sort(array, left + 1, end);//递归,右侧排序
		return array;
	} 
	public static void main(String[] args) {
		int[] arr = new int[] {8,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr, 0 , arr.length - 1)[i] + ",");
		}
	}
}

7、堆排序

package paixu;
/*堆排序:
选择排序的改进
将待排序的序列构成一个大顶堆(每个结点的值都大于或等于其左右孩子结点的值,称为大顶堆),
此时整个序列的最大值就是堆顶的根节点。
将它移走(其实就是将其与堆数组的末尾元素交换,此时末尾元素就是最大值),
然后将剩余的n-1个序列重新构造成一个堆,这样就会得到n个元素中的次最大值。
如此反复执行,就能得到一个有序序列了。
*/
public class heapSort {
	public static int[] sort(int[] array) {
		if(array.length == 0) {
			return array;
		}
		// 将待排序的序列构建成一个大顶堆
		for(int i = array.length / 2; i >= 0; i --) {
			heapAdjust(array, i, array.length);
		}
		// 逐步将每个最大值的根节点与末尾元素交换,并且再调整二叉树,使其成为大顶堆
		for(int i = array.length - 1; i > 0; i --) {
			swap(array,0,i); //将堆顶记录和当前未经排序子序列的最后一个记录交换
			heapAdjust(array, 0, i);//交换之后,需要重新检查堆是否符合大顶堆,不符合则要调整
		}
		return array;
	}
	//检查堆是否为大顶堆,若不符合则进行调整
	public static void heapAdjust(int[] array, int i, int n) {
		int child;
		int father;
		for(father = array[i]; leftChild(i) < n; i = child) {
			child = leftChild(i);
			//如果左子树小于右子树,则需要比较右子树和父节点
			if(child != n -1 && array[child] < array[child + 1]) {
				child ++;//序号增1,指向右子树
			}
			//如果父节点小于孩子结点,则需要交换
			if(father < array[child]) {
				array[i] = array[child];
			}else {
				break;//大顶堆结构未被破坏,不需要调整
			}
		}
		array[i] = father;
	}
	//获取到左孩子结点
	public static int leftChild(int i) {
		return 2 * i + 1;
	}
	//交换元素位置
	public static void swap(int[] array, int index1, int index2) {
		int temp = array[index1];
		array[index1] = array[index2];
		array[index2] = temp;
	}
	
	public static void main(String[] args) {
		int[] arr = new int[] {8,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr)[i] + ",");
		}
	}
}

8、计数排序

package paixu;
/*计数排序:
1、找出待排序数组A中的最大值和最小值;
2、统计数组A中每个值为i的元素出现的次数,存入数组C中的第i项;
3、将C中的每个i位置的元素大小改成C数组前i项和;
4、初始化一个跟A同样大小的数组B,倒序遍历A中元素,通过查找C,将元素放到B相应位置中,
同时将C中对应的元素大小-1(表明已经放置了一个这样大小的元素,下次再放同样大小的元素,
就要往前挤一个位置)。
*/
public class countingSort {
	public static int[] sort(int[] array, int k) {
		if(array.length == 0) {
			return array;
		}
		int sum = 0;
		int[] B = new int[array.length];
		int[] C = new int[k + 1];
		for(int i = 0; i < array.length; i ++) {
			C[array[i]] += 1;//统计数组A中个元素的个数,存入数组C中
		}
		for(int i = 0; i < k+1; i ++) {//修改数组C
			sum += C[i];
			C[i] = sum;
		}
		for(int i = array.length - 1; i >= 0; i--) {//遍历数组A,构造数组B
			B[C[array[i]]- 1] = array[i];//将A中该元素放到排序后数组B中指定的位置
			C[array[i]] --;//将C中该元素-1,方便存放下一个同样大小的元素
		}
		return B;
	}
	public static void main(String[] args) {
		int[] arr = new int[] {8,1,5,6,3,2};
		for(int i = 0; i < arr.length; i ++) {
			System.out.print(sort(arr, 8)[i] + ",");
		}
	}
}

参考:
https://www.cnblogs.com/guoyaohua/p/8600214.html
https://segmentfault.com/a/1190000014105591
https://tryenough.com/arithmetic-quitsort
https://www.cnblogs.com/developerY/p/3166462.html
https://blog.csdn.net/zdp072/article/details/44227317

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值