要想深刻理解歸併排序我們首先介紹一下分治法:
但解決問題時,首先將問題分解成若干個規模較小的與原問題類似的子問題;
然後遞迴地求解各個子問題;(當問題足夠小時,直接求解)
最後我們要合併這些分解而來的子問題(注意這是乙個與原問題不同的合併操作);
歸併排序完全遵循了分治模式:
首先要想將包含n各元素的陣列排序,我們分解問題為將兩個各具有n/2各元素的陣列排序;
然後遞迴地對這兩個陣列進行排序;(當待排序陣列的元素數量為1時,陣列當然是排好序的,我們就解決了問題,當然這裡也可以假設遞迴至陣列元素為2、3、4等時用別的方法來將他們排序)
最後我們合併兩個已經排好序的陣列為所求。
顯然合併兩個已經排好序的陣列是新產生的問題,解決它也是歸併演算法的關鍵所在,(個人認為這也是它名字的由來)。
下面是c++**:
#includeusing namespace std;
void merge_sort(int* arr, int p, int r,int * result);
void merge(int* arr, int p, int r,int* result);
int main() ;
int result[5];
merge_sort(arr, 0, 4,result);
//for (int i = 0; i < 5; i++)
}void merge_sort(int* arr, int p, int r,int* result)
else cout << endl; }}
void merge(int* arr, int p, int r, int* result)
else
result[k++] = arr[j++];
} while (i < q + 1)
while (j < r + 1)
for (int i = 0; i < r - p + 1; i++)
}
合併過程merge的操作就是比較然後排序,沒什麼花招,很容易懂。arr為待合併的陣列的原始所在,引數p,r分別為待排序陣列的起始下標和終止下標,陣列ruselt是為了儲存過程變數而存在的。
值得稱讚的是整個遞迴過程,遞迴的控制條件是r 是否等於 p,假設p=r,那麼意味著陣列長度為1,顯然已經排好序了。
下圖給出了簡單陣列執行歸併操作時的過程輸出。
歸併演算法的時間複雜度為θ(nlogn)
。值得好好去體會和理解一下qaq~
排序演算法之歸併排序
歸併排序也是經典的使用分治法思想的代表演算法之一。歸併排序的效率很高,而且是一種穩定的排序。其總體的思想思路就是將待排序的元素分成大致相同的兩個子集合,分別對兩個子集合進行排序,最終將排序的子集合合併成排好序的總集合 歸併排序c 實現如下 include void mergesort int arr...
排序演算法之歸併排序
歸併排序是建立在歸併操作上的一種有效的排序演算法。該演算法是採用分治法 divide and conquer 的乙個非常典型的應用,歸併排序將兩個已排序的表合併成乙個表。歸併排序基本原理 通過對若干個有序結點序列的歸併來實現排序。所謂歸併是指將若干個已排好序的部分合併成乙個有序的部分。歸併排序基本思...
排序演算法之歸併排序
歸併排序,和快排一樣同樣採用了分治的思想,將兩個 或以上 有序表合併成乙個新的有序表。歸併排序步驟如下 把n個記錄看成 n個長度為 1 的有序子表 進行兩兩歸併使記錄關鍵字有序,得到 n 2 個長度為 2 的有序子表 重複第2步直到所有記錄歸併成乙個長度為n的有序表為止。下面是歸併排序演算法的遞迴實...