思想:
在乙個已排好序的序列基礎上,每次將下乙個待排序記錄有序插入到已排好序的序列中,直到所有待排序記錄全部插入為止。
步驟:1. 剛開始排序時,可將陣列第乙個元素認為是已經有序(只有乙個數時肯定有序)
2. 接著依次從陣列第二個元素開始,到陣列最後乙個元素,每次順次取出乙個元素插入已排序序列中
3. 當待排序元素全部插入到已排序序列中時完成排序
注意:直接插入排序是利用插入的思想進行排序,是在本陣列裡邊完成的,不需要借助其他陣列空間。所謂的插入元素指的是從陣列第二個元素開始到陣列最後乙個元素(未排序序列),依次取出乙個元素插入到陣列已排序序列中。通俗來說,此時陣列分為兩部分:已排序序列+未排序序列。
待排序序列: 2 5 9 1 3 71)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 ...