快速排序法(詳解)

2021-09-24 21:29:07 字數 2867 閱讀 2361

假設對以下10個數進行快速排序:61

2793

45108

我們先模擬快速排序的過程:首先,在這個序列中隨便找乙個數作為基準數,通常為了方便,以第乙個數作為基準數。61

2793

45108

在初始狀態下,數字6在序列的第1位。我們的目標是將6挪到序列中間的某個位置,假設這個位置是k

kk。現在就需要尋找這個k

kk,並且以第k位為分界點,左邊的數都≤

6\le6

≤6,右邊的數都≥

6\ge6

≥6。那麼如何找到這個位置k

kk呢?

我們要知道,快速排序其實是氣泡排序的一種改進,氣泡排序每次對相鄰的兩個數進行比較,這顯然是一種比較浪費時間的。

而快速排序是分別從兩端開始」探測」的,先從右往左找乙個小於6的數,再從左往右找乙個大於6的數,然後交換他們。這裡可以用兩個變數i

ii和j

jj,分別指向序列最左邊和最右邊。我們為這兩個變數起個好聽的名字「哨兵i

ii」和「哨兵j

jj」。剛開始的時候讓哨兵i

ii指向序列的最左邊,指向數字6。讓哨兵j

jj指向序列的最右邊,指向數字8。61

2793

45108

ij首先哨兵j

jj開始出動。因為此處設定的基準數是最左邊的數,所以需要讓哨兵j

jj先出動,這一點非常重要。哨兵j

jj一步一步地向左挪動(即j=j

−1j = j-1

j=j−

1),直到找到乙個小於6的數停下來。接下來哨兵i

ii再一步一步向右挪動(即i=i

+1i=i+1

i=i+

1),直到找到乙個數大於6的數停下來。最後哨兵j

jj停在了數字5面前,哨兵i

ii停在了數字7面前。61

2793

45108

ij現在交換哨兵$i$和哨兵$j$所指向的元素的值。交換之後的序列如下。 61

2593

47108

ij到此,第一次交換結束。接下來開始哨兵j

jj繼續向左挪動(再友情提醒,每次必須是哨兵j先出發)。他發現了4

<

64<6

4<

6,停下來。哨兵i

ii也繼續向右挪動的,他發現了9

>

69>6

9>

6,停下來。此時再次進行交換,交換之後的序列如下。61

2543

97108

ij第二次交換結束。哨兵j

jj繼續向左挪動,他發現了3

<

63<6

3<

6,又停下來。哨兵i

ii繼續向右移動,此時哨兵i

ii和哨兵j

jj相遇了,哨兵i

ii和哨兵j

jj都走到3面前。說明此時「探測」結束。我們將基準數6和3進行交換。交換之後的序列如下。31

2546

97108

i,j

到此第一輪「探測」真正結束。現在基準數6已經歸位,此時以基準數6為分界點,6左邊的數都小於等於6,6右邊的數都大於等於6。回顧一下剛才的過程,其實哨兵j

jj的使命就是要找小於基準數的數,而哨兵i

ii的使命就是要找大於基準數的數,直到i

ii和j

jj碰頭為止。

現在我們將第一輪「探測"結束後的序列,以6為分界點拆分成兩個序列,左邊的序列是「3 1 2 5 4」,右邊的序列是「9 7 10 8」。接下來還需要分別處理這兩個序列。因為6左邊和右邊的序列目前都還是很混亂的。不過不要緊,我們已經掌握了方法,接下來只要模擬剛才的方法分別處理6左邊和右邊的序列即可。現在先來處理6左邊的序列現吧。31

2546

重複第一輪的過程,應該得到如下序列:21

3546

ok,現在3已經歸位。接下來需要處理3左邊的序列:21

36處理之後,2已經歸位,序列「1」只有乙個數,也不需要進行任何處理,因此「1」也歸位。12

36對於基數右邊的序列,採用和左邊相同的過程;最終將會得到這樣的序列,如下。12

3456

78910

細心的同學可能已經發現,快速排序的每一輪處理其實就是將這一輪的基準數歸位,直到所有的數都歸位為止,排序就結束了。接下來用圖示的方法來展示完整的過程:

快速排序之所以比較快,是因為與氣泡排序相比,每次的交換時跳躍式的,每次排序的時候設定乙個基準點,將小於等於基準點的數全部放到基準點的左邊,將大於等於基準點的數全部放到基準點的右邊。這樣在每次交換的時候就不會像氣泡排序一樣每次只能在相鄰的數之間進行交換,交換的距離就大的多了。因此總的比較和交換次數就少了,速度自然就提高了。當然在最壞的情況下,仍可能是相鄰的兩個數進行了交換。因此快速排序的最差時間複雜度和氣泡排序是一樣的都是o(n

2)o(n^2)

o(n2

),它的平均時間複雜度為o(n

log⁡2n

)o(n\log_2n)

o(nlog2​

n)。實現快速排序的**如下:

void

quick_sort

(int

*arr,

int begin,

int end)

} arr[begin]

= arr[i]

; arr[i]

= tmp;

quick_sort

(arr, begin, i-1)

;quick_sort

(arr, i+

1, end)

;}

快速排序法

一 快速排序演算法的基本特性 時間複雜度 o n lgn 最壞 o n 2 空間複雜度 o n lgn 不穩定。快速排序是一種排序演算法,對包含n個數的輸入陣列,平均時間為o nlgn 最壞情況是o n 2 通常是用於排序的最佳選擇。因為,基於比較的排序,最快也只能達到o nlgn c void q...

快速排序法

include stdafx.h include vos.h define table mid machine name midmachine define table midmach colname id id define table midmach colname ip ip define t...

快速排序法

快速排序法思想 在待排序的n個資料中取第乙個數字為基準數,陣列最前面放乙個標桿,陣列最後麵放乙個標桿,通過基準數和標桿 i,j 出的數進行比較,實現每次排序完時候,共三組數,不大於基準數 基準數 不小於基準數 舉例說明 5 i 4,6,8,3,9,2 j 基準數5 標桿 i 指向5位置,標桿 j 指...