個人算法學習筆記:算法基礎之——SelectionSort,InsertionSortjava
選擇排序動態演示
選擇排序示例:
git
public class SelectionSort{
// 排序算法中不會產生任何實例
private SelectionSort(){}
public static void sort(Comparable[]arr){
for(int i=0;i<arr.length;i++){
int minIndex = i;
for(int j=i+1;j<arr.length;j++){
if(arr[minIndex].compareTo(arr[j])>0){
minIndex = j;
}
}
Comparable temp = arr[minIndex];
arr[minIndex] = arr[i];
arr[i] = temp;
}
}
}
複製代碼
插入排序動態演示
插入排序又叫撲克牌排序,我我的以爲撲克牌排序(PorkerSort)要比InsertionSort這個名字更讓人理解這個排序的過程。咱們在和別人打鬥地主的時候,將一張牌又一張牌抓在手裏的過程,這個過程實際上咱們就應用了插入排序這種思想。示例:
github
將插入排序的過程轉換爲Java代碼:算法
public class InsertionSort{
// 算法中不會產生任何實例
private InsertionSort(){}
public static void sort(Comparable[]arr){
for(int i=1;i<arr.length;i++){
for(int j=i;j>0;j--){
if(arr[j].compareTo(arr[j-1])<0){
Comparable temp = arr[j];
arr[j] = arr[j-1];
arr[j-1] = temp;
}else{
break;
}
}
}
}
}
複製代碼
在代碼中,第一個for循環for(int i=1;i<arr.length;i++)
,爲何i的取值是從1開始的呢?其實也不難想到,在咱們抓到第一張牌的時候,這張牌已是「排好序」的一張牌了,在咱們從抓第二張牌開始,纔會考慮到和手中的第一張牌做比較並排序的事情。另外本例的代碼還能夠在語法糖上進行簡化:數組
public class InsertionSort{
private InsertionSort(){}
public static void sort(Comparable[]arr){
for(int i=1;i<arr.length;i++){
for(int j=i;i>0 && arr[j].compareTo(arr[j-1]);j--){
Comparable temp = arr[j];
arr[j] = arr[j-1];
arr[j-1] = temp;
}
}
}
}
複製代碼
相比於選擇排序,插入排序彷佛要好那麼一些。選擇排序是一個"純正的"O(n^2)級別的算法,由於選擇排序不管如何都會堅持本身的使命,執行完代碼。而插入排序則不一樣,當新插入的元素比較到某個位置時發現它沒有這個位置的元素大,那麼程序就會break出這層循環。能夠形象地理解爲:選擇排序是「不撞南牆不回頭」,插入排序則更像是「見好就收」。試想一下:若是一個數組爲已經排好序的數組,可是咱們不知道它爲一個已經排好序的數組,須要使用某個算法對其進行排序,若是咱們使用了選擇排序,很顯然選擇排序依然會消耗O(n^2)的時間複雜度,而插入排序則不一樣,插入排序會從一個O(n^2)級別的算法進化爲一個O(n)級別的算法!如今對SelectionSort及InsertionSort進行測試。 測試代碼:測試
bash
仔細分析插入排序與選擇排序,其實不難發現,出現上述測試結果的主要緣由就在swap(交換)上。插入排序算法,每插入一個元素,當發現被插入的元素小於前面的元素時,咱們馬上就讓兩者swap,若是繼續比較,被插入的元素仍然小於前面的元素,還要再次進行swap。插入排序的優化思想就是讓swap這個過程變爲一個簡單的賦值過程。如示例:
待插入的元素爲:「5」,先將元素「5」存儲起來。
學習
public class InsertionSort{
// 算法中不會產生任何實例
private InsertionSort(){}
public static void sort(Comparable[]arr){
for(int i=1;i<arr.length;i++){
Comparable temp = arr[i];
int j;
for(j=i;j>0;j--){
if(temp.compareTo(arr[j-1]){
arr[j] = arr[j-1];
}
}
arr[j] = temp;
}
}
}
複製代碼
經測試,優化過的插入排序在時間上有了必定的壓縮。雖然作了幾回測試,優化的插入排序與選擇排序在時間上不分上下,可是須要知道的是插入排序的意義就在於對幾乎排好序的數據來講,時間複雜度近乎爲O(n),這個特性是選擇排序所沒有的。測試