- 内部排序
- 插入排序
- 思想:将n个数组看成一个有序表和一个无序表,开始时有序表只有一个元素,排序过程是每次取出无序表中的第一个元素,将它的排序码与有序表中元素的排序码进行比较,将其放在合适的位置
public static void insertSort(int[] array) { for (int i = 1;i<array.length;i++){ int insertIndex=i-1; int insertVal=array[i]; while (insertIndex>=0&&insertVal<=array[insertIndex]){ array[insertIndex+1]=array[insertIndex]; insertIndex--; } array[++insertIndex]=insertVal; } }
- 直接插入排序
- 希尔排序
- 思想:将n个数组看成一个有序表和一个无序表,开始时有序表只有一个元素,排序过程是每次取出无序表中的第一个元素,将它的排序码与有序表中元素的排序码进行比较,将其放在合适的位置
- 选择排序
- 思想:对于数组arr[n],从小到大:第一次从从arr[0]到arr[n-1]选一个最小值与arr[0]交行,第二次从arr[1]到arr[n-1]选一个最小值与arr[1]交换,以此类推,通过n-1次得到有序序列。从大到小排序,与从小到大的方式一样,只是每次选出最大值
public static void selectSort(int[] array) { for (int i = 0;i<array.length-1;i++){ int min=array[i]; int minIndex=i; for (int j = i+1;j<array.length;j++){ if(array[j]<min){ min=array[j]; minIndex=j; } } if(minIndex!=i){ array[minIndex]=array[i]; array[i]=min; } } }
- 简单选择排序
- 堆排序
- 思想:对于数组arr[n],从小到大:第一次从从arr[0]到arr[n-1]选一个最小值与arr[0]交行,第二次从arr[1]到arr[n-1]选一个最小值与arr[1]交换,以此类推,通过n-1次得到有序序列。从大到小排序,与从小到大的方式一样,只是每次选出最大值
- 交换排序
- 冒泡排序
- 代码
public static void bubbleSort(int[] array) { // for(int i = 0;i<array.length;i++){ // for(int j = 0;j<array.length-i-1;j++){ if(array[j]>array[j+1]){ int temp = array[j]; array[j]=array[j+1]; array[j+1]=temp; } } } }
- 优化:在每轮循环过程中,若有元素有交换,数列无序;若无元素交换,说明数列已然有序,直接跳出大循环
public static void bubbleSort(int[] array) { //数组循环的轮数 for (int i = 0;i<array.length;i++){ //有序标记,每轮初始值都是true boolean flag = true; for (int j = 0;j<array.length-i-1;j++){ if(array[j]>array[j+1]){ int temp = array[j]; array[j]=array[j+1]; array[j+1]=temp; //若数组不是有序的将有序标记设置为false flag = false; } } //有序标记为true时,说明数组是有序的,跳槽循环 if(flag){ break; } } }
- 优化:添加边界,每轮循环后,边界之后的元素肯定是有序的,无须比较,所以下轮循环时只需要比较边界前的数列
public static void bubbleSort(int[] array) { //最后一次交换的位置 int lastExchangeIndex = 0; //边界下标,边界前面的为无序数列,边界后面的为有序数列,每轮循环只需要比到此处 int sortBorder=array.length-1; //数组循环的轮数 for (int i = 0;i<array.length;i++){ //有序标记,每轮初始值都是true boolean flag = true; for (int j = 0;j<sortBorder;j++){ if(array[j]>array[j+1]){ int temp = array[j]; array[j]=array[j+1]; array[j+1]=temp; //若数组不是有序的将有序标记设置为false flag = false; //最后一次交换的位置 lastExchangeIndex = j; } } //有序标记为true时,说明数组是有序的,跳槽循环 if(flag){ break; } //每轮循环后,将边界设置为最后交换的位置 sortBorder=lastExchangeIndex; } }
- 升级:鸡尾酒排序
public static void bubbleSort(int[] array) { //左边界,边界左边为有序数列 int leftSortBorder=0; //右边界,边界右边为有序数列 int rightSortBorder=array.length-1; //向右比对时最后一次交换的位置 int lastRightExchangeIndex =0; //向左比对时最后一次交换的位置 int lastLeftExchangeIndex =0; for (int i = 0;i<array.length;i++){ boolean flag = true; //从左往右,大的向后移动 for (int j = leftSortBorder;j<rightSortBorder;j++){ if(array[j]>array[j+1]){ int temp = array[j]; array[j]=array[j+1]; array[j+1]=temp; lastRightExchangeIndex=j; flag=false; } } rightSortBorder=lastRightExchangeIndex; if(flag){ break; } //从右往左,小的向前移动 flag = true; for (int j = rightSortBorder;j>leftSortBorder;j--){ if(array[j]<array[j-1]){ int temp = array[j]; array[j]=array[j-1]; array[j-1]=temp; lastLeftExchangeIndex=j; flag=false; } } leftSortBorder=lastLeftExchangeIndex; if(flag){ break; } } }
- 代码
- 快速排序
- 冒泡排序
- 归并排序
- 基数排序
- 介绍:
- 属于分配式排序
- 效率高的稳定性排序
- 桶排序的扩展
- 以空间换时间,可能会出现OutOfMemoryError错误
- 思想:将数组中所有的数据统一为同样的数位长度,数位较短的数前面补零,然后从最低位开始比较,依次进行排序,直到最高位排序完成后,数列就是一个有序的数列
- 例子:数组{26,8,500},排序后{8,26,500}
- 代码:
public static void radixSort(int[] array) { //获取最大元素的位数 int max = array[0]; int arrLength = array.length; for (int i =1;i<arrLength;i++){ if(array[i]>max){ max=array[i]; } } int maxLenght=(max+"").length(); //二维数组表示10个桶,每个桶都是一个一位数组,存放array中的元素 int[][] bucket = new int[10][arrLength]; //桶中每次放入的数据个数 int[] bucketElementCounts = new int[10]; //排序 for (int i =0,n=1;i<maxLenght;i++,n*=10){ //将元素放到桶中 for (int j = 0;j<arrLength;j++){ //元素各位的值,各位、十位、百位... int digitOfElement = array[j]/n % 10; //将元素放到对应的桶中 bucket[digitOfElement][bucketElementCounts[digitOfElement]]=array[j]; bucketElementCounts[digitOfElement]++; } int index = 0; //遍历桶 for(int j = 0;j<10;j++){ //如果桶中有元素,遍历桶,此处必须用bucketElementCounts[j] if(bucketElementCounts[j]>0){ //依次将桶中的元素放到原数组中 for(int k = 0;k<bucketElementCounts[j];k++){ array[index++]=bucket[j][k]; } } //将桶中的元素的个数置为0 bucketElementCounts[j]=0; } } }
- 介绍:
- 插入排序
- 外部排序