漫談經典排序演算法:三、冒泡排序 && 快速排序

來源:互聯網
上載者:User
1、序言

這是《漫談經典排序演算法系列》第三篇,先解析了冒泡排序,然後引出快速排序,給出了快速排序的兩種實現版本。

各種排序演算法的解析請參考如下:

《漫談經典排序演算法:一、從簡單選擇排序到堆排序的深度解析》

《漫談經典排序演算法:二、各種插入排序解析及效能比較》

《漫談經典排序演算法:三、冒泡排序 && 快速排序》

《漫談經典排序演算法:四、歸併排序》

《漫談經典排序演算法:五、線性時間排序(計數、基數、桶排序)》

《漫談經典排序演算法:六、各種排序演算法總結》

 

註:為了敘述方便,本文以及原始碼中均不考慮A[0],預設下標從1開始。

2、冒泡排序          2.1 引出

           前面的兩篇部落格裡講的插入排序是基於“逐個記錄插入”,選擇排序是基於“選擇”,那麼冒泡排序其實是基於“交換”。每次從第一個記錄開始,一、二兩個記錄比較,大的往後放,二三兩個記錄比較...依次類推,這就是一趟冒泡排序。每一趟冒泡排序後,無序序列中值最大的記錄冒到序列末尾,所以稱之為冒泡排序。

          2.2 代碼
//冒泡排序void bubbleSort(int *a,int n){int i,j;for(i=1;i<n;i++)for(j=1;j<n-i+1;j++){if(a[j+1]<a[j]){a[j]=a[j]+a[j+1];a[j+1]=a[j]-a[j+1];a[j]=a[j]-a[j+1];}}}
          2.3 效率分析

相對於簡單選擇排序,冒泡排序交換次數明顯更多。它是通過不斷地交換把最大的數冒出來。冒泡排序平均時間和最壞情況下(逆序)時間為o(n^2)。最佳情況下雖然不用交換,但比較的次數沒有減少,時間複雜度仍為o(n^2)。此外冒泡排序是穩定的。

3、快速排序          3.1 引出

           快速排序是冒泡排序的一種改進,冒泡排序排完一趟是最大值冒出來了,那麼可不可以先選定一個值,然後掃描待排序序列,把小於該值的記錄和大於該值的記錄分成兩個單獨的序列,然後分別對這兩個序列進行上述操作。這就是快速排序,我們把選定的那個值稱為樞紐值,如果樞紐值為序列中的最大值,那麼一趟快速排序就變成了一趟冒泡排序。

          3.2 代碼

           兩種版本,第一種是參考《資料結構》,在網上這種寫法很流行。第二種是參考《演算法導論》,實現起來較複雜。

//快速排序(兩端交替著向中間掃描)void quickSort1(int *a,int low,int high){int pivotkey=a[low];//以a[low]為樞紐值int i=low,j=high;if(low>=high)return;//一趟快速排序while(i<j){//雙向掃描while(i < j && a[j] >= pivotkey)j--;a[i]=a[j];while(i < j && a[i] <= pivotkey)i++;a[j]=a[i];}a[i]=pivotkey;//放置樞紐值//分別對左邊、右邊排序    quickSort1(a,low,i-1); quickSort1(a,i+1,high); }//快速排序(以最後一個記錄的值為樞紐值,單向掃描數組)void quickSort2(int *a,int low,int high){int pivotkey=a[high];//以a[high]為樞紐值    int i=low-1,temp,j;if(low>=high)return;//一趟快速排序for(j=low;j<high;j++){if(a[j]<=pivotkey){i++;            temp=a[i];a[i]=a[j];a[j]=temp;}}i++;//放置樞紐值temp=a[i];a[i]=pivotkey;a[high]=temp;//分別對左邊、右邊排序    quickSort2(a,low,i-1); quickSort2(a,i+1,high); }
          3.3 效率分析

        快速排序時間與劃分是否對稱有關。快速排序的平均時間複雜度為o(n*logn),至於為什麼是o(n*logn),請參考《演算法導論》第7章,書中用遞迴樹的方法闡述了快速排序平均時間。且常數因子很小,所以就平均時間而言,快速排序是很好的內部排序方法。最佳情況下(每次劃分都對稱)時間複雜度o(n*logn)。最壞情況下(每次劃分都不對稱,如輸入的序列有序或者逆序時)時間複雜度為o(n^2),所以在待排序序列有序或逆序時不宜選用快速排序。此外,快速排序是不穩定的。

        最佳情況下,每次劃分都是對稱的,由於樞紐值不再考慮,所以得到的兩個子問題的大小不可能大於n/2,同時一趟快速排序時間為o(n),所以已耗用時間遞迴運算式:

T(n)<=2T(n/2)+o(n)。這個遞迴式的解法請參考下一篇部落格中歸併排序效率分析。其解為T(n)=o(n*logn)。

        最壞情況下,每次劃分都很不對稱,T(n)=T(n-1)+o(n),可以用遞迴樹來解,第i層的代價為n-i+1.總共有n層。把每一層代價加起來有n-1個n相加。所以這個遞迴式的解為T(n)=o(n^2),此時就是冒泡排序。

4、附錄         4.1 參考書籍

          《資料結構》嚴蔚敏版                    《演算法導論》

           4.2 所有原始碼
#include<stdio.h>//冒泡排序void bubbleSort(int *a,int n){int i,j;for(i=1;i<n;i++)for(j=1;j<n-i+1;j++){if(a[j+1]<a[j]){a[j]=a[j]+a[j+1];a[j+1]=a[j]-a[j+1];a[j]=a[j]-a[j+1];}}}void main(){int i;int a[7]={0,3,5,8,9,1,2};//不考慮a[0]bubbleSort(a,6);for(i=1;i<=6;i++)printf("%-4d",a[i]);printf("\n");}
#include<stdio.h>//快速排序(兩端交替著向中間掃描)void quickSort1(int *a,int low,int high){int pivotkey=a[low];//以a[low]為樞紐值int i=low,j=high;if(low>=high)return;//一趟快速排序while(i<j){//雙向掃描while(i < j && a[j] >= pivotkey)j--;a[i]=a[j];while(i < j && a[i] <= pivotkey)i++;a[j]=a[i];}a[i]=pivotkey;//放置樞紐值//分別對左邊、右邊排序    quickSort1(a,low,i-1); quickSort1(a,i+1,high); }//快速排序(以最後一個記錄的值為樞紐值,單向掃描數組)void quickSort2(int *a,int low,int high){int pivotkey=a[high];//以a[high]為樞紐值    int i=low-1,temp,j;if(low>=high)return;//一趟快速排序for(j=low;j<high;j++){if(a[j]<=pivotkey){i++;            temp=a[i];a[i]=a[j];a[j]=temp;}}i++;//放置樞紐值temp=a[i];a[i]=pivotkey;a[high]=temp;//分別對左邊、右邊排序    quickSort2(a,low,i-1); quickSort2(a,i+1,high); }void main(){int i;int a[7]={0,3,5,8,9,1,2};//不考慮a[0]quickSort2(a,1,6);quickSort1(a,1,6);for(i=1;i<=6;i++)printf("%-4d",a[i]);printf("\n");}

 

 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.