常用排序、選擇演算法

來源:互聯網
上載者:User

1 插入排序

插入排序的左邊是有序的,依次從右邊拿出一個數,插入到左邊,直到右邊沒有更多的數,此時左邊的數已經全部按序排列。

插入排序的C語言實現

void insertion_sort(int array[], int length){int i,j;for(i=1;i<length;i++){for(j=i;j>0;j--){if(array[j]<array[j-1]){int temp = array[j];array[j] = array[j-1];array[j-1] = temp;}elsebreak;}}}

插入排序的平均時間複雜度是O(N^2),當輸入序列已經排好序的情況下,可以達到O(N)。所以當數組已經部分排好序的情況下,插入排序的效率較高。

這裡是一個關於插入排序的舞蹈視頻:http://t.cn/hros0W 。不管怎麼樣,視頻只能協助你理解排序的一個總體思路,但是只有切身用代碼實現了,才算是真正會了,有時候少一個等號,迭代少了一次,都會導致結果的錯誤。至於完全理解每個演算法的適用場合,還需要在工作中的不斷經驗積累,以及良好的數學功底。

2 冒泡排序 Bubble Sort

冒泡大概是最好理解的一個排序演算法之一了,不過我第一次接觸的時候也花了一些時間才明白過來。從名字上來看,冒泡排序就像是水裡的泡泡一樣,最大的元素不斷的浮出水面,排到整個數組的最後。具體的說,第一次迭代,最大的元素會排到數組最後,第二次迭代,次大的元素會排到數組的倒數第二,第三次迭代,第三大的元素會排到數組的倒數第三……以此類推。

冒牌排序的平均時間複雜度是O(N^2),最壞的情況是O(N^2),最優情況O(N)。

冒泡排序的C實現代碼:

void bubbleSort(int arr[],int len){int i,j;int flag;for(i = 0;i < len;i++){flag = 0;for(j = 0; j < len -i -1; j++){if(arr[j]>arr[j+1]){//swap arr[j], arr[j+1];int tmp = arr[j];arr[j] = arr[j+1];arr[j+1] = tmp;flag = 1;}}/*if in this loop, flag has never been changed, then the whole array is already sorted*/if(flag == 0){break;}}}

冒泡排序的舞蹈視頻:http://t.cn/hrf58M

3 快速排序

快速排序如它的名字一樣,是速度最快的排序之一。快速排序的平均時間複雜度是O(NlogN),最壞的情況是O(N^2)

快速排序是一種遞迴排序演算法,首先選擇一個pivot軸心元素,讓數組中比pivot小的元素排到其左邊,比它大的元素排到右邊。然後再遞迴用快速排序整理pivot左邊的部分,以及右邊的部分。直到整體實現有序。這裡使元素分別排到pivot兩邊的演算法叫partition分區演算法。最好的pivot選取是選擇一個數組的中數median,如果不巧選到了一個數組裡的Max or Min,就會導致最壞情況的發生。具體的分析就不在這裡說了。如果想知道去看看CLRS演算法導論,裡面有詳細的partition演算法,還有關於如何選取一個好的pivot。

快速排序的C語言簡單實現:

void quicksort(int array[],int left,int right){int index = partition(array,left,right);/*recursively sort the left part*/if(left<index-1){quicksort(array,left,index-1);}/*recursively sort the right part*/if(index<right){quicksort(array,index,right);}}/*return the index of pivot element*/int partition(int array[],int left,int right){int pivot = array[(left+right)/2];while(left<right){/*find the element that should on right side of pivot*/while(array[left]<pivot){left++;}/*find the element that should on left side of pivot*/while(array[right]>pivot){right--;}/*swap left and right*/if(left<=right){int tmp = array[left];array[left] = array[right];array[right] = tmp;left++;right--;}}return left;}

同樣在最後給出舞蹈視頻:http://t.cn/ScTA1d

4 歸併排序 Merge Sort

一直想不通為什麼要把Merge翻譯成歸併…

Merge Sort也用到了遞迴,更確切的說法是用到了Divide and Conquer的分治思想,分:把一個數組分成2段,先將左邊排序,再將右邊排序,合:最後融合到一個數組裡。

虛擬碼:

void mergeSort(

        left = mergeSort(array, 0, middle);

        right  = mergeSort(array, middle, end);

        merge(left, right);

}

Merge Sort的平均和最壞的時間複雜度都是O(NlogN),至於怎麼得出的可以參看演算法導論CLRS,簡單的說一下:設時間複雜度是T(n),那麼從上面虛擬碼可以推出遞迴式:T(n) = 2T(n/2) + O(n), 這裡的O(n)最後merge過程的時間複雜度,可以求出T(n)是O(NlogN),有個公式的,你也可以推理或者猜一個答案來反證,總之方法很多,如果你本科演算法課好好聽了應該會有印象。

簡單的說一下Merge過程,現在有兩個排好了序的數組,然後要融合它們,怎麼做?分別從兩個數組的頭部開始迭代,逐個比較,小的那個拿走,直到迭代完成。

Merge Sort的C語言實現:

void mergeSort(int a[],int start,int end){if(start<end){int mid = (start+end)/2;mergeSort(a,start,mid);mergeSort(a,mid+1,end);merge(a,start,mid,end);}}void merge(int a[], int start, int mid, int end){int i = start;//copy array a into a temporary helper arrayint helper[end];while(i<=end){helper[i] = a[i];i++;}//start to merge left part and right partint left = start;int right = mid+1;//pointer 'current' is pointing at current index of array 'a'int current = start;while(left <= mid && right <= end){if(helper[left]<=helper[right]){a[current] = helper[left];left++;}else{a[current] = helper[right];right++;}current++;}//copy the remaining of left part into array 'a'while(left <= mid){a[current] = helper[left];current++;left++;}}

還有一點關於merge過程想說的,上面的最後,只需要copy左半部分剩下的到原數組裡,為什麼呢?因為右半部分如果有剩下,那麼它已經在原數組裡正確的位置上了。

例如,merge這樣一個數組的左右兩個部分:2 3 7 || 1 8 9, 左邊會先被迭代光,此時右邊還剩8和9,但是位置已然已經正確了;再例如 1 8 9 || 2 3 7 ,這時候就是左邊會剩下,需要迭代完。

最後給出merge sort的視頻 http://v.youku.com/v_show/id_XMzMyODk5Njg4.html

面試的很少會直接考你排序,一般都是夾在在某些題目裡。稍後我會更新一些題目上來。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.