插入排序定义
选择排序的整体思想,就是将当前位置的元素和前一个元素进行对比, 如果当前位置比较小,则交换它俩的位置,然后继续往前进行对比交换,直到前一个元素不比后一个元素小为止。
代码实现
public static void insertSort(int[] arr) {
int len = arr.length;
for(int i=0; i<len; i++) {
for(int j=i; j>0 && arr[j] < arr[j-1]; j--) {
swap(arr, j, j-1); //如果后一个数比前一个数小,则交换
}
}
System.out.println("insertSort: "+Arrays.toString(arr));
}
private static void swap(int[] arr, int i, int j) {
int temp = arr[j];
arr[j] = arr[i];
arr[i] = temp;
}
插入排序优化
在刚刚的代码中,我们每比较一次,就进行一次交换,而从上面的交换方法中可以看到,每次交换实际上有三步操作。如果我们把每次要往前插入的值记录下来,前面大的数直接赋值给后一个位置,等找到合适位置时,再直接把值插入即可,这样每次就从三步操作简化为一步操作, 代码如下:
public static void insertSort2(int[] arr) {
int len = arr.length;
int insertValue = -1;
for(int i=1; i<len; i++) {
insertValue = arr[i];//记录下当前位置的值
int j=i;
for(; j>0 && arr[j-1] > insertValue; j--) {
arr[j] = arr[j-1];//如果前一个值比较大,则往后移
}
arr[j] = insertValue;//插入到合适的位置
}
System.out.println("insertSort: "+Arrays.toString(arr));
}
虽然依然是一个时间复杂度为O(n^2)的排序算法,但是依然有常数级的优化效果。
附上自动生成测试数组的代码
public static int[] randomArray(int length) {
int[] arr = new int[length];
Random random = new Random();
for(int i=0; i<length; i++) {
arr[i] = random.nextInt(100);
}
//自动生成随机数组,先进行一次原始数据打印
System.out.println(Arrays.toString(arr));
return arr;
}
总结
由于插入排序的特性,如果要排序的数据越趋向于有序,则排序越快,甚至比O(nLogn)级别的算法还要快。所以插入排序可以用于小规模排序或者近乎有序的数据排序。
另外,还可以对插入排序经过一个较大的优化,不过由于效率的改变太明显,所以重新命名为了
希尔排序
,下一章将单独讲到希尔排序。
版权声明:本文为qq475703980原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。