插入排序(insertion sort)

插入排序是最简单的排序算法之一,其算法复杂度为O(n^2),最好的情况是O(n)。

算法简介
其实我们在打扑克牌时,就已经用到排序算法了。我们左手拿着的是已经排序号的扑克牌,右手从牌堆里抽取一张未排序的扑克,和左右的扑克从右向左意义比较知道找到这张牌的位置,将其插入到左手的牌中。

算法很简单,有几点需要注意的:
1,为什么是从右向左比较?
当要排序的数据是以数组(array)形式储存,而在一个数组中插入一个数据的算法复杂度为O(n)。所以,如果我们很笨拙从左向右比较,那么这个算法的最好情况怎么会出现?对于第i个元素,我们要比较i-1次才能找到它的位置。那么算法最优情况就变成了,1+2+...+n次操作,复杂度为O(n^2),故最优情况O(n),不会出现。
而且,前面提到在数组中插入一个数的复杂度为O(n)。故,当我们对第i个元素进行排序时,找到其位置需要操作为j,那么将这个数插入到数组中,需要的操作为(i-j)。所以,对第i个元素进行排序的操作一定是i步操作。所以如果从左向右的话,那么这个算法就不会出现最优情况了。
但是,如果我们是对双向列表(double-linked list)进行插入排序的话,那么。从左向右,或者从右向左排序就都没有关系了。前者的最有情况是列表时反序的,后者是顺序的。

代码
package sorting;

public class Data {
	
	/**
	 * generate an unsorted array of length n
	 * @param n length
	 * @param max the maximum integer element of this array
	 * @return an unsorted array consists of elements range from 1 to max
	 */
	public static int[] getArray(int n, int max){
		int[] result = new int[n];
		for(int i =0; i < n; i++){
			result[i] = (int)(Math.random() * max + 1);
		}
		return result;
	}
	/**
	 * print the array
	 * @param arg array
	 */
	public static void printArray(int[] arg){
		StringBuffer temp = new StringBuffer();
		for(int i = 0; i < arg.length; i++){
			temp.append(arg[i] + "\t");
		}
		System.out.println(temp);
	}
}

package sorting;

public class InsertionSort {

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		InsertionSort is = new InsertionSort();
		int[] data = Data.getArray(10, 100);
		System.out.print("Source data:\t");
		Data.printArray(data);
		is.intsertionSort(data);
		System.out.print("Sorted data:\t");
		Data.printArray(data);
	}
	/**
	 * sort the array in ascending order
	 * @param arg
	 */
	public void intsertionSort(int[] arg){
		int j = 0;
		int key = 0;
		for(int i =1; i < arg.length; i++){
			key = arg[i];
			for( j = i -1; j >= 0; j--){
				if(arg[j] > key){
					arg[j + 1] = arg[j];
					arg[j] = key;
				}else{
					break;
				}
			}
		}
	}

}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值