歸併排序(Merging Sort)就是利用歸併的思想實現的排序方法。它的原理是 假設初始序列含有 n 個記錄,則可以看成
是 n 個有序的子序列,每個子序列的長度爲 1,然後兩兩歸併,得到 [n/2] ( [x]表示不小於 x 的最小整數 ) 個長度爲 2 或
爲 1 的有序子序列;兩兩歸併,……,如此重複,直到得到一個長度爲 n 的有序序列爲止,這種排序方法稱爲 2路歸併排序。
java實現:
public static void Merge_Sort(int[] arr)
{
MSort(arr, arr, 0, arr.length-1);
}
public static void MSort(int[] SR, int[] TR1, int s, int t)
{
int m;
int[] TR2 = new int[SR.length];
if(s == t)
TR1[s] = SR[s];
else
{
m = (s + t)/2; //將SR[s..t]平分爲SR[s..m] 和 SR[m+1..t]
MSort(SR, TR2, s, m); //遞歸將SR[s..m]歸併爲有序的TR2[s..m]
MSort(SR, TR2, m+1, t); //遞歸將SR[m+1..t]歸併爲有序TR2[m+1..t]
Merge(TR2, TR1, s, m, t); //將TR2[s..m] 和 TR2[m+1..t]歸併到TR1[s..t]
}
}
//將有序的SR[i..m] 和 SR[m+1..n] 歸併爲有序的 TR[i..n]
public static void Merge(int[] SR, int[] TR, int i, int m, int n)
{
int j, k, l;
for(j = m + 1, k = i; i <= m && j <= n; k++) //將SR中記錄由小到大歸併入TR
{
if(SR[i] < SR[j])
TR[k] = SR[i++];
else
TR[k] = SR[j++];
}
if(i <= m)
{
for(l = 0; l <= m - i; l ++)
TR[k+l] = SR[i+l]; //將剩餘的SR[i..m]賦複製到TR
}
if(j <= n)
{
for(l = 0; l <= n-j; l ++)
TR[k+l] = SR[j+l];
}
}
時間複雜度,一趟歸併需要將SR[1]~SR[n]中相鄰的長度爲 h 的有序序列進行兩兩歸併。並將結果放到 TR1[1]~TR[n]中,
這需要將待排序序列中的所有記錄掃描一遍,因此耗費 O(n)時間,而由完全二叉樹的深度可知,整個歸併排序需要
進行 [logn]([x]表示不大於x的最小整數),因此總的時間複雜度爲O(nlogn), 而且這是歸併排序算法中最好,最壞,平均的時間性能。
由於歸併排序在歸併過程中需要與原始記錄序列同樣數量的存儲空間存放歸併結果以及遞歸時深度爲 log₂n 的棧空間,因此空間複雜度爲 O(n+logn)。
另外,Merge函數中有if ( SR[i] < SR[j] )語句,說明taxuyao它需要兩兩比較,不存在跳躍,因此歸併排序是一種穩定的排序算法。歸併排序是一種 比較佔內存,但卻效率高且穩定的算法。