假設你的計算機存儲了很多音樂,對於每首音樂,你都記錄了其播放次數。
那么你需要將這個音樂列表按播放次數從多到少進行排序。假設這個列表的長度是 n
首先遍歷這個列表,找出播放次數最多的歌曲,將其放到一個新列表的第一位,操作遍歷 次數為 n
然后再次編譯剩下的列表,找出播放次數最多的歌曲,把它放到排序列表的第二位,操作遍歷 次數 為 n-1
以此類推操作遍歷次數為 n-2;...2;1
這樣最終得到一個有序列表,這就是選擇排序。選擇排序是一種靈巧的算法,但是速度不快。
選擇排序的最終操作次數為(n+n-1...+2+1),也就是 n 的遞減的和,運行效率書上是記做 O(n2),其實是O((n2-n)/2)
那么n+n的遞減的和為:(n2+n)/2
/**
* java選擇排序
* @param arr 數組
*/
public void selectionSort(Comparable[] arr){
int N= arr.length; //數組長度
int count=0; // 統計排序次數
for (int i = 0; i < N; i++) {
int min =i;
//這里糾正下網上一些同學 int j = i; j < N; j++ 的寫法,既然 已經 min=i,那么i 就不用跟他自己比較了,直接比較后面一個
for (int j = i+1; j < N; j++){
count++;
if (arr[j].compareTo(arr[min])<0) { //判斷判斷當前數值是否小於最小值
min = j;
}
}
//交互數組順序,思路是每一次找到最小的,然后放到 i 的位置(第一次是最小的,第二次是第二小的)
Comparable c =arr[i];
arr[i] =arr[min];
arr[min] =c;
}
}
有人認為選擇排序比 冒泡排序要快,是真的嘛?
/**
* 冒泡排序
* @param arr
*/
public void maoPaoSort(Integer[] arr){
int counts=0;//冒泡排序次數
for(int i=0;i<arr.length-1;i++){ //外層循環 n-1 ,控制比較輪數
for(int j=0;j<arr.length-1-i;j++){ //內層循環 n-1-i ,控制每一輪比較次數
counts++;
if(arr[j]>arr[j+1]){ //兩兩比較做交換 ,判斷大小交換位置
int number=arr[j];
arr[j]=arr[j+1];
arr[j+1]=number;
}
}
}
}
測試結果
其實可以看到它們循環比較的次數都是一樣的。但是為什么說選擇排序比冒泡排序要快呢?
仔細看代碼,你會發現選擇排序的數組位移在外層循環,而冒泡排序的位移在內循環。
因此選擇排序比冒泡排序效率要高