排序演算法小結(冒泡排序、簡單選擇排序、快速排序)

來源:互聯網
上載者:User

排序演算法小結(冒泡排序、簡單選擇排序、快速排序)

    1)冒泡排序bubble_sort
        1.原理
            假設對a[N]進行排序
            依次比較相鄰兩個數,小數放前,大數放前。
            *1    從頭開始進行第一輪比較,則得到最後一個位置是所有數中的最大的一個數;       
                需要比較的次數是N-1,為什麼是N-1?因為,總共是N個數,數組下標是從0開始,
                如果比較最後兩個資料,判斷條件:if(a[N-1-1] > a[N-1]),a[N-1]就是數組的最後一個數了,
                如果比較次數是N,則執行該論最後一對資料比較時就是if(a[N-1] > a[N]),
                眾所都知,a[N]中是沒有a[N],所以次數會得到一個意想不到的排序,裡面會多一個垃圾值,垃圾值的產生就是a[N]。
                所以此時必須用N-1。
            *2    從頭開始進行第二輪比較,則得到倒數第二個位置是所有數中的次最大數;       
                需要比較的次數是(N-1)-1,為什麼是(N-1)-1?因為,解釋同上。
            *3    從頭依次進行第三輪比較,則得到倒數第三個位置是所有數中的次次最大數;       
                需要比較的次數是N-1-1-1,為什麼是(N-1)-1-1?因為,解釋同上。
            *N-1    依次從頭開始比較,直至比較完。
        2.代碼實現過程
            void bubble_sort(int a[], int N)            //N是數組a的長度
            {
                int i, j, tmp;

                for(i = 0; i < N-1; i++)            //進行比比較的趟數,此時的N-1如果換成N,對程式影響不大,只不過多一次迴圈而已
                {
                    for(j = 0; j < N-i-1; j++)        //開始進行比較,此時的N-i-1不能換成N-i,如果寫成N-i,會產生一個垃圾值,解釋在*1中
                    {
                        if(a[j] > a[j+1])
                        {
                            tmp    = a[j];
                            a[j]   = a[j+1];
                            a[j+1] = tmp;
                        }
                    }
                }
               
                return;
            }
   
    2)簡單選擇排序select_sort
        1.原理
            假設對a[N]進行排序
            假定選一個最小的,依次把後面的數與它進行比較,如果後面的比假定選的最小的還小,則進行交換這兩個數。每進行一輪就要找出一個最小的數。
            *1    第一輪    假定第一個數是“最小的”,然後依次把後面的數與這個“最小的”的進行比較,如果比這個“最小的”小,首先標記該數為“最小的”,
                    然後把這個“最小的”與前面的“最小的”交換值,目的是保證第一個數是後面所有數中最小的一個。
            *2    第二輪    因為已經知道第一個是最小的,這時從第二個開始尋找最小的,假定第二個是最小的,然後依次把後面的數與這個“最小的”的進行比較,
                    如果比這個“最小的”小,首先標記該數為“最小的”,然後把這個“最小的”與前面的“最小的”交換值,目的是保證第二個數是後面所有數中最小的一個。

            *N    第N輪    步驟同上。
           
            說明    是進行N輪比較還是N-1輪比較,影響不大,原因是:該數組中共有N個數,如果對N-1個數進行了排序處理,即第N-1個數是後面中最小的一個數,
                剩餘的唯一的第N個數肯定是所有數中最大的,顯然它應該放在最後一個位置上,沒必要再進行一次迴圈。如果是進行N輪比較,無非是程式多執行一次迴圈,
                其實實際上這次迴圈也沒有執行,因為在子迴圈中無法滿足迴圈條件,不能執行迴圈體。

        2.代碼實現過程
            void select_sort(int a[], int N)        //N是數組a的長度
            {
                int i, j, min, tmp;

                for(i = 0; i < N; i++)            //從頭開始比較
                {
                    min = i;            //把第i個數當作最小的,把下標標記為min
                    for(j = i+1; j < N; j++)    //把a[min]依次和它後面的數進行比較
                    {
                        if(a[j] < a[min])    //如果後面的某個值比a[min]小
                        {
                            min = j;    //重新標記最小值下標
                        }
                        tmp = a[min];        //交換
                        a[min] = a[i];        //原來min = i的,如果沒有找到比a[min]小的,就不進行交換(如果沒找到,i還是和min一樣,執行該三條語句沒作用)
                        a[i] = tmp;        //只有a[j] < a[min]成立,執行了min = j,這時才能交換(這時min的已經改為j,不再是i了,所以執行才有作用)
                    }                //自己表達欠缺,上面三句表達不夠明確,只要自己研讀程式,因該能明白其中奧妙
                }

                return;
            }

    3)快速排序quick_sort
        1.原理
            假定對a[N]排序
            快速排序使用分治法(Divide and conquer)策略來把一個序列(list)分為兩個子序列(sub-lists)。
            實現快速排序需要兩個函數,分別是:partition()和quick_sort()
           
            函數:            int partition(int a[], int i, int j)
            函數功能:        把數組分為兩段,左段都是比基準小的數,但是左段的數是無序的;右段都是比基準大的數,但是右段的數是無序的。
            函數大概實現過程:       
                    *1    選取一個基準(pivot),基準一般選取第一個數a[0];

                    *2    定義兩個變數i、j;
                        令j從數組尾部向左掃描,直到遇到一個數比基準小的,進行交換。目的是:使比基準小的都放在基準左邊。
                        令i從數組開頭向右掃描,直到遇到一個數比基準大的,進行交換。目的是:使比基準大的都放在基準右邊。
                        進行多次迴圈後,最終i的值就是基準應該放的位置。
                        原因是:我們假定的基準是數組的第一個數a[0],a[0]也許既不是數組中最大的數也不是數組中最小的數,
                        也就是基準的位置應該在數組中的某個位置,經過多次迴圈後,i不斷往後遞增,當不滿足迴圈條件時,i就停止了,此時i就是基準的位置
                        (表達欠缺,還需要自己揣摩)
               
            函數:            void quick_sort(int a[], int left, int right)
            函數功能:        實現排序
            函數大概實現過程:
                        遞迴的對每一段進行排序

        2.代碼實現過程
            int partition(int a[], int i, int j)
            {           
                int pivot;                //基準
       
                pivot = a[i];               
                while(i < j)
                {
                    while(i < j && a[j] > pivot);   
                    {
                        j--;            //如果右邊的比基準大,左移j
                    }
                    a[i] = a[j];            //如果遇到了右邊的比基準小,和基準交換
               
                    while(i < j && pivot <= a[i]);
                    {
                        i++;            //如果左邊的基準小,右移i
                    }
                    a[j] = a[i];            //如果遇到了左邊的比基準大,和基準交換
                }
                a[i] = pivot;

                return i;
            }

            void quick_sort(int a[], int left, int right)
            {
                int pivottag;
           
                if(left < right)
                {
                    pivottag = partition(a, left, right);
                    quick_sort(a, 0, pivottag-1);   
                    quick_sort(a, pivottag+1, right);
                }

                return;
            }

聯繫我們

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