插入排序算法的实现和思考

//直接插入排序

public class InsertSort {
	//让数组中的数字从小到大排列
	public static void main(String[] args) {
		
		 int a[] = {49, 38, 65, 97, 76, 13, 27, 49, 78, 34, 12, 64, 5, 4, 62, 99, 98, 54, 56, 17, 18, 23, 34, 15, 35, 25, 53, 51};  
		 int temp = 0;
		 
		 for (int i = 1; i < a.length ; i++) {
			 int j = i - 1;
			 temp = a[i]; //a[i]是要插入的那个数,将数值负值给temp
			 for (; j >= 0 && temp < a[j]; j--) {
				 a[j+1] =a [j]; //将大于temp的值整体后移一个单位  
			 }
			 a[j+1] = temp;
		 }
		 for (int i = 0; i < a.length; i++) {
			 System.out.print(a[i] + " ");
		 }
	}

}


基本思想在要排序的一组数中,假设前面(n-1)[n>=2] 个数已经是排好顺序的,现在要把第n个数插到前面的有序数中,使得这n个数也是排好顺序的。如此反复循环,直到全部排好顺序。

在编辑的过程中还是要时不时去翻看原来的代码,虽然之前背过但是忘得七七八八。自己试着写的时候发现写不出

来,着实感到很羞愧。最后还是相当于把代码抄了一遍吧……

在自己试着写算法的过程中发现主要是有两个难点:

1. i 和j 的值定义的位置,是应该作为局部变量还是作为全局变量定义呢?在for的初始化表达式里定义还是在for循环前面定义(第一个初始化表达式,第二个循环变量判定表达式,第三个循环变量修正表达式)。

答:这里要搞清楚temp和a[i]的关系,当temp被赋值插入的数,a[i]代表的是当前已插入数组的最后一个位置的数。

2.代码中的j=i-1;但是什么时候用i-1,什么时候用j也是需要注意的。

答:当我把第16行的a[j+1]错写成i的时候,排序错误。算法的逻辑出现了错误。

然后我试着将上述的算法进行修改成由大到小排序的结果。

//直接插入排序

public class InsertSort2 {
	//让数组中的数字从小到大排列
	public static void main(String[] args) {
		
		 int a[] = {49, 38, 65, 97, 76, 13, 27, 49, 78, 34, 12, 64, 5, 4, 62, 99, 98, 54, 56, 17, 18, 23, 34, 15, 35, 25, 53, 51};  
		 int temp = 0;
		 
		 for (int i = 1; i < a.length ; i++) {
			 int j = i - 1;
			 temp = a[i]; //a[i]是要插入的那个数,将数值负值给temp
			 for (; j >= 0 && temp > a[j]; j--) { //仅仅改变判断符号即可
				 a[j+1] =a [j]; //将小于temp的值整体后移一个单位  
			 }
			 a[j+1] = temp;
		 }
		 for (int i = 0; i < a.length; i++) {
			 System.out.print(a[i] + " ");
		 }
	}

}

结果还是错将第13行写成 a[j] = a[j+1]; 导致逻辑出现错误排序失败。


直接插入排序的时间复杂度,数组长度为n:

1、最优情况:当给出的序列是已经按要求排好序的时候,每个插入的数只需与前面的数比较一次,(外层for循环)循环n-1趟,每一趟只进行一次比较,但是并不发生交换,也就是说循环体中的内容没有被执行到,但是内层for循环的判断表达式也执行了n-1次,所以复杂度为O(n)。(这里有一点要注意:不交换并不代表没有进行比较!)。

2、最坏情况:当给出的序列是按照要求相反的顺序进行排序的,外层for循环循环n-1趟,那么每一趟的比较次数分别为1,2,3……n-1,一共比较(n-1)(n-1+1)/2≈n²/2次,时间复杂度为O(n^2)。

3、平均时间复杂度是O(n^2)。


空间复杂度:算法中用了一个temp变量来存放临时数据。所需要的辅助存储空间对输入量来说是一个常数,所以空间复杂度为O(1)。


稳定性:排序完成后,相同的数之间的相对位置并没有发生改变,稳定。


适用情况:直接插入排序适用于初始记录基本有序(正序)的情况,当初始记录无序,n较大时,此算法时间复杂度较高,不宜采用。


总结:了解并不等于理解,只知道思想还需知道如何实现,就算简单的算法也要去实践,不断剖析才能真正地理解更深,才能掌握。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值