希爾排序

基本思想:

        希爾排序是把記錄按下標的必定增量分組,對每組使用直接插入排序算法排序;隨着增量逐漸減小,每組包含的關鍵詞愈來愈多,當增量減至1時,整個文件恰被分紅一組,算法便終止。java

個人理解:

分治法的方式,將整個數組拆分紅若干個小的數組,進行一個簡單的直接插入排序。算法

希爾排序就是在直接插入排序的基礎上進行改進的。所以,若是想要理解希爾排序,就先須要瞭解直接插入排序,並且當把二者放在一塊兒的時候,更加容易進行記憶。數組

-----------------------------------------------------------------------------------------------------dom

源代碼:

插入排序的java代碼:

import java.util.Random;
/**
 * 直接插入排序,說白了,就類比打撲克,拿一張  插一張,插入到合適的位置
 * 當拿下一張的時候,保證你在手中的這部分都已經排好順序了。
 * @author chf
 *
 */
public class Insertion{
	public static void main(String[] args) {
		int[] arr= new int[10];
		for(int i=0;i<arr.length;i++){
			arr[i]=new Random().nextInt(100);
			
		}
		System.out.println("排序前");
		for (int i : arr) {
			System.out.print(i+" ");
		}
		System.out.println();
		InsertionSort(arr);
		System.out.println("排序後");
		for (int i : arr) {
			System.out.print(i+" ");
		}
	}
	public static void InsertionSort(int[] arr){
		//起始位置是 第 1 號位置,由於 0 沒有比較的對象,這樣子 默認 0號位置就是已經排好序的。
		for(int i=1;i<arr.length;i++){
			//每次循環的開始  前面的 那部分數組 已經排好序了,後面的只須要跟前面的已經排好序的進行比較
			for(int j=i;j-1>=0;j-=1){
				//ps 上面的 for 循環裏面的條件之因此不寫 j-- 是爲了跟 希爾排序作對比
				//若是 當前位置的 元素 比當前位置的前一個元素大或者相等,就break,不用比較了
				if(arr[j]>=arr[j-1]){
					break;
				}
				//若是不 break;就符合條件,進行交換
				//即當前位置的元素小於 當前位置的前一個元素
				//省去中間變量,其實還能夠用 位運算符
				arr[j]=arr[j]+arr[j-1];//arr[j]=arr[j]^arr[j-1];
				arr[j-1]=arr[j]-arr[j-1];//arr[j-1]=arr[j]^arr[j-1];
				arr[j]=arr[j]-arr[j-1];//arr[j]=arr[j]^arr[j-1];
				
				//不過要注意的就是若是 兩個位置的數組 是相等的 ^ 運算會成 0
				
				
			}
		}
	}
}

希爾排序的 java代碼:

import java.util.Random;
/**
 * 希爾排序 就是 增強版的 直接插入排序
 * @author chf
 *
 */
public class Shell {
	public static void main(String[] args) {
		int[] arr= new int[10];
		for(int i=0;i<arr.length;i++){
			arr[i]=new Random().nextInt(100);
			
		}
		System.out.println("排序前");
		for (int i : arr) {
			System.out.print(i+" ");
		}
		System.out.println();
		ShellSort(arr);
		System.out.println("排序後");
		for (int i : arr) {
			System.out.print(i+" ");
		}
	}
	public static void ShellSort(int[] arr){
		int h=1;
		//首先計算步長,步長也能夠直接是數組 長度的一半,而後每次 除以2 就行
		while(h<arr.length/3){
			h=h*3+1;
		}
		//當步長大於0,也就是等於1的時候,結束後跳出循環
		while(h>0){
			//直接插入排序是從1 開始,由於 默認 第一個已經排好順序
			//這裏面加入了步長,所以默認從 步長的位置開始
			//將 0 - h 直接的 數組元素先屏蔽掉,將 0 跟 h 這兩個單獨的元素 組成一個數組
			for(int i=h;i<arr.length;i++){
				//在直接插入排序中,  h 就是1
				//若是將全部的h 變成1 就跟 直接插入排序是如出一轍的了
				//所以當 步長爲1的時候,其實就是直接插入排序了
				for(int j=i;j-h>=0;j-=h){
					//排在後面的大,就進行插入排序
					if(arr[j]>=arr[j-h]){
						break;
					}
					arr[j]=arr[j]+arr[j-h];//arr[j]=arr[j]^arr[j-h];
					arr[j-h]=arr[j]-arr[j-h];//arr[j-h]=arr[j]^arr[j-h];
					arr[j]=arr[j]-arr[j-h];//arr[j]=arr[j]^arr[j-h];
					
				}
				
				
			}
			
			//每次步長縮短
			h=(h-1)/3;
		}
	}
}

-------------------------------------------------------------------------------spa

這兩個代碼放一塊,希爾排序就好記了不少code

---------------------------------------------------------------------------------對象

不保證代碼徹底正確,也不保證代碼是最優。排序

僅僅是根據本身的理解,寫出來直觀的代碼,方便理解。io

錯誤請指出,感激涕零!class

相關文章
相關標籤/搜索
本站公眾號
   歡迎關注本站公眾號,獲取更多信息