純手擼——歸併排序
阿新 • • 發佈:2020-08-17
思想:
- 分治思想——把一個複雜龐大的問題分解成一個個小的問題去解決(就好比輔導員管班長,班長管寢室長,寢室長管寢室成員)
- 歸併排序,就是將待排序的數分成兩半後排好序,然後再將兩個排好序的序列合併成一個有序序列
- 需要開闢輔助空間,在合併時運用(如下圖,假設將最後的arr看成新的空間,就是不斷取出最小的元素放在裡面比較一下,取完後這個新空間裡的元素有序)
閱讀篇:慧能大師講解歸併排序
看圖入門:
程式碼實現(難度在合併,理解後還算簡單):
//將a[left...center]和a[center+1...right]兩個有序數組合併成一個有序陣列 void merge(int a[],int tmp[],int left,int center,int right) { int i=left; int j=center+1; //比較結果暫放入tmp for(int k=left;k<=right;k++) { //若左邊陣列取完,則比較完成,直接將右邊陣列copy到臨時陣列 //右邊陣列同理 if(i>center) { tmp[k]=a[j++]; } else if(j>right) { tmp[k]=a[i++]; } else if(a[i]<=a[j]) { tmp[k]=a[i++]; } else { tmp[k]=a[j++]; } } //再將排好序的臨時陣列回copy for(int h=left;h<=right;h++) { a[h]=tmp[h]; } } void MergeSort(int a[],int tmp[],int left,int center,int right) { if(left<right) { //[分]:陣列一分為二 int center=(left+right)/2; //[治]:將左邊陣列排序 MergeSort(a,tmp,left,center); //[治]:將右邊陣列排序 MergeSort(a,tmp,center+1,right); //[合]:合併兩個有序陣列 merge(a,tmp,left,center,right); } }