直接插入排序 希爾排序 Java實現

2021-08-30 06:32:22 字數 4069 閱讀 1158

思想:

在乙個已排好序的序列基礎上,每次將下乙個待排序記錄有序插入到已排好序的序列中,直到所有待排序記錄全部插入為止。

步驟:1. 剛開始排序時,可將陣列第乙個元素認為是已經有序(只有乙個數時肯定有序)

2. 接著依次從陣列第二個元素開始,到陣列最後乙個元素,每次順次取出乙個元素插入已排序序列中

3. 當待排序元素全部插入到已排序序列中時完成排序

注意:直接插入排序是利用插入的思想進行排序,是在本陣列裡邊完成的,不需要借助其他陣列空間。所謂的插入元素指的是從陣列第二個元素開始到陣列最後乙個元素(未排序序列),依次取出乙個元素插入到陣列已排序序列中。通俗來說,此時陣列分為兩部分:已排序序列+未排序序列。

待排序序列:        2    5    9    1    3    7

1)59    1    3    7其中紅色部分表示已排好序的部分

2)91    3    7藍色數字表示此次需要插入的元素

3)         1    3    7                      黑色部分表示待排序部分

4)         3    7

5)         7

6)

public void insert() 

arr[j + 1] = arr[j];//否則將key之前的元素順序後移

}arr[j + 1] = key;//將key插到相應位置

}}

複雜度分析: 

1.時間複雜度

最好情況:所給陣列已經有序,此時只需要依次取出陣列未排序序列的元素並直接插入,省去了移動元素的時間。所以此時的時間複雜度為o(n);

最壞情況:所給陣列逆序,此時外層迴圈依次取出陣列未排序序列的元素,內層迴圈將該元素之前的元素全部依次往後移動乙個位置,即插入第 i 個元素時要移動 i -1 次。所以此時的時間複雜度為o(n^2);

所以,直接插入排序的時間複雜度為o(n^2)。

2.空間複雜度

由於完成此次排序只需要乙個輔助空間,即存放key的空間,所以空間複雜度為o(1)。

穩定性判斷:

從內層迴圈的條件語句if (key > arr[j])中我們可以知道,只有當要插入的元素比它之前的元素大時,才會移動之前的元素。當遇到和自己相等的元素時並不會進行移動操作,即要插入的元素不會出現在跟它相同的元素的前面 --> 所以,直接插入排序是乙個穩定的排序演算法。

待排序序列:        2    5    7    1    3    7

1)57    1    3    7其中紅色部分表示已排好序的部分

2)71    3    7藍色數字表示此次需要插入的元素

3)13    7黑色部分表示待排序部分

4)37

5)7

6)

適用場景:

由於直接插入排序最好情況下的時間複雜度為o(n),所以特別適用於待排序記錄數目較少且基本有序的情況。

完整**:

//直接插入排序

public class insertsort

public void insert()

arr[j + 1] = arr[j];//否則將key之前的元素順序後移

}arr[j + 1] = key;//將key插到相應位置}}

public void print()

system.out.println();

}}

思想:

希爾排序又稱縮小增量排序,也是一種基於插入思想的排序方法。即每次排序不是按順序排,而是以gap=gap/3+1的間隔排序(),其中gap初始值為size,在由間隔分割成的每個子串行進行插入排序。

步驟:1. 以gap=gap/3+1為間隔,在整個待排序序列中將所有間隔為gap的記錄分成一組,進行組內直接插入排序(gap初始值為陣列大小)

2. 重複步驟1,直到gap為1,此時只有乙個子串行,對該序列進行直接插入排序,完成排序。

待排序序列:        2    5    7    1    3    7

取gap=3,分為間隔為3的子串行:       257

137

各子串行內進行插入排序,結果為:    137

257

取gap=2,分為間隔為2的子串行:       137

257           其中相同顏色的記錄表示同乙個子串行

各子串行內進行插入排序,結果為:     125

377

取gap=1,分為間隔為1的子串行:       1

2 5    3    7    7

各子串行內進行插入排序,結果為:     1    2    3    5    7    7

public void shell() }}

private void _shell(int gap) else

}arr[j + gap] = key;

}}

複雜度分析:

1.時間複雜度:

最好情況:所給陣列已經有序,此時時間複雜度為o(n);

最壞情況:所給陣列逆序,此時時間複雜度為o(n^2);

所以,希爾排序的時間複雜度為o(n^1.3)。

2.空間複雜度

由於排序過程中只需要乙個輔助空間key,所以空間複雜度為o(1)。

穩定性判斷:

希爾排序不穩定。如待排序序列為。排序前2在 2 前面,排序後2在 2 後面。

待排序序列:    2      4      1       2

取gap=2,分為間隔為2的子串行:     241

2各子串行內進行插入排序,結果為12

24 

取gap=1,分為間隔為1的子串行:12

24 各子串行內進行插入排序,結果為:12

24

適用場景:

儘管當gap為1時相當於直接插入排序,但是由於此時序列已經基本有序,恰好是直接插入排序的最好情況,所以希爾排序是乙個較好的排序方法,適用於對中等規模(n<=1000)的序列進行排序。

完整**:

public class shell 

public void shell() }}

private void _shell(int gap) else

}arr[j + gap] = key;}}

public void print()

system.out.println("");

}}

直接插入排序 希爾排序

一.直接插入排序 原理 將陣列分為無序區和有序區兩個區,然後不斷將無序區的第乙個元素按大小順序插入到有序區中去,最終將所有無序區元素都移動到有序區完成排序。最優複雜度 當輸入陣列就是排好序的時候,複雜度為o n 而快速排序在這種情況下會產生o n 2 的複雜度。最差複雜度 當輸入陣列為倒序時,複雜度...

直接插入排序 希爾排序

1.直接插入排序 時間複雜度o n2 工作原理 通過構建有序序列,對於未排序資料,在已排序的序列中,從後向前掃瞄,找到相應的位置並插入。插入排序在實現上,在從後向前掃瞄的過程中,需要反覆把已排序元素逐步向後移動,為最新元素提供插入空間。直接插入排序 public static void insert...

插入排序 直接插入 希爾排序

直接插入排序是將元素按順序插入已經排好序的序列中。對於待插入的元素,如果比最後乙個元素還大,則不用處理。否則,從後邊元素開始比較,並順次後移,直到碰到元素小於或者等於該元素。設定第乙個元素位置為哨兵,用來存放待插入元素。include include include using namespace ...