1. 程式人生 > >常用的排序演算法詳解(C#版)

常用的排序演算法詳解(C#版)

只要是搞程式設計的演算法、資料結構、作業系統、計算機組成原理這些東西都會有用到,就像醫生給人治病一樣,只有瞭解了人的內部機理、運作機制,才能很好的做到對症下藥,藥到病除。而上面所說的那些計算機理論課就好像人的內部機理一樣,我們往往都把這些東西給忽略了,而把更多的精力放在具體的程式語言實現上,當然我也是這樣,上學的時候這些計算機理論課都沒怎麼好好學,覺得這些東西很枯燥無味,最重要的是在我那時期的那個層次跟本看不到這些東西有什麼用,學了很長時間的程式語言然後再回來看,發現只有對這些基礎理論性的東西有更深刻的體會,才能做出更高效、更優秀的專案。

資料結構和演算法一直都學得不好,總是當時看了理解的挺好,時間一長就有些忘了,而且這個東西在實際的開發中雖然有用但較之於程式設計的實現而言畢竟用的少些,熟能生巧吧,學習就是這樣,不斷的練習、總結,然後昇華、提高,成為自己的東西。下面就把常用的幾種演算法總結分析下和大家分享,希望能對你們有所幫助。如果有說的不對的地方,還請朋友們多多指教!

一、氣泡排序演算法

氣泡排序演算法,就像它的名字一樣生動形象,這個演算法需要內外迴圈兩次,外迴圈是控制整體的排序次數,外排次數=陣列長度-1,關於這個也很好理解,比如10個數只要其他的9個位置確定了最後一個位置也就確定了,所以外排序的次數就是陣列總個數減去1.內排序主要是控制每次的排序比較,之所以稱之為冒泡就是因為每次排序的開始都是從陣列的最後一位依次跟前一位比,就像氣泡從水底冒出來一樣,所以稱之為氣泡排序

下面的具體演算法實現:

Private static void MaoPao()

{

Int [ ] shuJu=new int [int]{ 12,43,2,34,87,54,32,16,67,49};

For(int i=1;i<=shuJu.Length-1;i++)

{

   For(int j=shuJu.Length;j>=i;j--)

    {

      If(shuJu[j]<shuJu[j-1])

        {

         Int temp=shuJu[j];

         shuJu[j]=shuJu[j-1];

         shuJu[j-1]=temp;

        }

   }

}

二、選擇排序

選擇排序的原理,第一次從陣列中選出最小的數,將它放在陣列的第一位置,第二次再從陣列中選出最小的數,將它放置在第二個位置,以後每次都選出最小的數,按照上邊的排序方式,放置在陣列中合適的位置,這樣到最後選出的數就是有序的。

具體程式碼實現:

Private void static XuanZe()

{

Int [ ] shuJu=new int [int]{ 12,43,2,34,87,54,32,16,67,49};

Int  min,temp;//分別用來標記最小的陣列中最小數的下表,和儲存臨時資料(數字交換時使用)

For(int i=0;i<shuJu.Length-1;i++)

{

     Min=i;//標記下表為(當前的排序次數-1)的陣列數字為當前的最小值

     For(int j=i+1;j<shuJu.Length;j++)//依次和陣列中的其他資料進行比較,如果其他資料有比當前標記的最小值小的,則陣列最小值下表賦值為兩者之間較小值的下標

     {

       If(shuJu[j]<shuJu[min])

        {

           Min=j;

        }

        Temp=shuJu[i];

        shuJu[i]=shuJu[min];

        shuJu[min]=temp;

     }

}

三、插入排序

插入排序的原理是:每次向陣列中插入一個數,將插入的數與之前插入的有序的數進行比較,如果大於之前插入的數,則直接插入,如果小於之前插入的數,則進行交換後再插入,這樣到最後插入的數全部都是有序的。

具體程式碼實現:

Private static void ChaRu()

{

Int [ ] shuJu=new int [int]{ 12,43,2,34,87,54,32,16,67,49};

Int temp;

For(int i=1;i<shuJu.Length;i++)

{

   Int t=shuJu[i];//標記為排序的資料

   Int j=i;

While(j>0 && shuJu[j-1]>t) 如果當前未排資料小於上一個資料,且當前j大於0,則將上一個資料移致當前的資料所在的下標位置,同時j下標要減一,

{

   shuJu[j]=shuJu[j-1];

   j--;

}

shuJu[j]=t;

}

}

四、快速排序演算法

快速排序演算法的原理是:主要用到了“分治”的思想,先將陣列中找到任意一個數為基準分成兩部分,一般是用陣列的中間元素,並且使左邊部分的數字全部小於基準數字,右邊的部分全部大於基準數字,然後在遞迴呼叫快速排序分別對左右區間進行排序,這樣形成的陣列就是有序的了。分治思想就是將原問題分解為若干個規模更小但結構與原問題相似的子問題。遞迴地解這些子問題,然後將這些子問題的解組合為原問題的解。

具體程式碼實現:

private static void KaiSu(int[] shuJu,int left,int right)

        {

              shuJu=new int [int]{ 12,43,2,34,87,54,32,16,67,49};

            int a=left-1;//左區域

            int b=right+1;//右區域

            int mid = shuJu[(left + right) / 2];//基準數字

            if (left < right)

            {

                while (true)

                {

                    while (shuJu[++a] <mid)

                        ;

                    while (shuJu[--b] > mid)

                        ;

                    if (a >= b)

                    {

                        break;

                    }

                    int temp = shuJu[a];

                    shuJu[a] = shuJu[b];

                    shuJu[b] = temp;

                }

                KaiSu(shuJu, left, a );//再遞迴呼叫對左區域進行排序

                KaiSu(shuJu, b, right);//遞迴呼叫對右區域進行排序

        }

嗯,到這裡常用的四種排序都介紹完了,各種排序有各的好處,氣泡排序比較容易理解,但是少量的資料還行,資料量大的話效率會很低,選擇排序則是對氣泡排序的一個升級,插入排序的話也比較容易理解,效率也比氣泡排序高些,快速排序的效率很高,同時因為用到了遞迴函式呼叫對記憶體的開銷會比較大一些,但整體來講效率還是要比其他幾種排序高的。

當然還有其他的一些排序,比如歸併排序、堆排序、基數排序等,這些都不太容易理解,有興趣的朋友可以去了解下!