排序演算法已經完成了兩篇了《選擇,插入,冒泡》,《希爾排序》 繼續把常用的演算法完成掉,下面我們來討論下關於歸併排序,快速排序,這兩種高階排序演算法。這兩種演算法是線性的也即對於o(nlogn)的排序演算法。
歸併排序:
歸併排序用的是分治(divide and conquer)的思想(分治也是乙個很不錯的演算法)。首先我們把給出的數列平分為左右兩段,然後對兩段數列分別進行排序,最後用剛才的合併演算法把這兩段(已經排過序的)數列合併為乙個數列。
下面我們來看一些例子:
la = (3,5,8,11)
lb = (2,6,8,9,11,15,20)
lc=(2,3,5,6,8,8,9,11,11,15,20)
上面的la和lb已經是有序序列了,由於兩個數列已經有序了,我們會發現輸出lc數列的第乙個數肯定為la的第乙個數或者lb的第乙個數.
第乙個輸出lb的2,然後再輸出la的3
形成這樣的數列
la=(5,8,11)
lb=(6,8,9,11,15,20)
然後再迴圈上面的操作,就可以排序了。也就是進行遞迴的操作。
下面看下演算法實現:
code:
voidmerge(int*a,intlen1,intlen2)
for(inti=0;i
a1[len1]=a2[len2]=int_max;
for(inti=0,j=0,k=0;k
else
} deletea1;deletea2;
}快速排序:
當然如果想更完美點還要對基準關鍵字左右的分治區間進行劃分演算法。
下面是演算法的大致思路過程:
初始狀態:【49,38,65,97,76,13,27,49】
一次劃分後:【27,38,13】 49【76,97,65,49】
分別進行快速排序: 27 【49,65】76
有序序列 【13,27,38,49,49,65,76,97】
演算法**(php實現):
code:
#include
voidquicksort(int*b,intleftlimit,intrightlimit)
while(b[right]>b[pivot_point]&&(right>leftlimit))
if(left<=right)//把最大值交換到最後 }
while(left<=right);
if(leftlimit
if(rightlimit>left) }
intmain(void)
quicksort(a,0,9);
for(inti=0;i<10;i++)//輸出排序後的數 }
}
排序演算法(2) 歸併排序,快速排序
分治思想 思想 將兩個有序的陣列歸併成乙個有序陣列。下面兩種歸併方法用到 建立乙個適當大小的陣列,然後將兩個有序陣列乙個個有序的放入所建立的陣列中 在此造成了額外的空間儲存問題 方法簽名 merge array,lo,hi 將子陣列a lo.mid a mid 1.hi 歸併,並將結果放入大a lo...
排序演算法(2) 歸併排序 快速排序
穩定原地排序 時間複雜度 空間複雜度 歸併排序 o n logn o n 快速排序 o n logn 歸併排序的合併函式,在合併兩個有序陣列為乙個有序的時,需要借助額外的儲存空間 public class mergesort private static void mergesortinternal...
排序演算法 氣泡排序,歸併排序,快速排序
氣泡排序 屬於交換排序的一種。很好理解的交換排序是這樣的 for int i 0 i n i for int j i 1 j n j 這個演算法的邏輯是從頭到尾掃瞄元素,將這個元素和它後面的所有元素進行比較,如果有比它更小的,那就交換,最後交換的一定是最小的,然後元素指標i後移,再比較它後邊的所有元...