1. 程式人生 > >演算法 直接插入排序小述

演算法 直接插入排序小述

一、概述

本節主要簡單介紹一下直接插入排序演算法,直接插入排序(Straight Insertion Sort)是一種最簡單的排序方法,其基本操作是將一條記錄插入到已排好的有序表中,從而得到一個新的、記錄數量增1的有序表。摘自百度百科

二、分析

假如現在有一個具有n+1個元素的序表,即table[0, n],現將該序表組成元素分為有序和待排序兩部分,預設即tableSorted[0, 1)和tableToBeSorted[1, n],隨後我們將tableToBeSorted待排序列表中的第0個元素插入到tableSorted有序列表之中,組成新的有序列表和待排序列表,即tableSorted[0, 1]和tableToBeSorted[2, n],重複此操作,直到待排序列表元素個數為0,即序表元素全部有序

三、程式碼展示

根據自己對於直接插入排序演算法的理解,我將演算法思路分成了三步,首先我們需要確定待排序數字在有序列表中的插入位置,其次我們將有序列表中該位置後的元素統一往後挪一位,最後我們將待排序數字放在該位置上,正序程式碼如下:

    // 這是根據定義寫的思路程式碼,不是最終程式碼
    private static int[] insertionSort(int[] dataToBeSorted) {
        int length = dataToBeSorted.length;
        for(int i=1; i<length; i++) {
            // 將待排序數字儲存起來
int temp = dataToBeSorted[i]; // 記錄插入的位置 int index = i; for(int j=i-1; j>=0; j--){ // 為了更直觀,判斷語句就不放在迴圈體裡了 if(dataToBeSorted[j] > dataToBeSorted[i]){ // 記錄待排序數字應該插入的位置 index--; }
else{ break; } } if(index != i){ // 在有序數列裡,將插入位置後面的數字,統一往後挪一位 for(; i>index; i--){ dataToBeSorted[i] = dataToBeSorted[i-1]; } // 在需要插入的位置上,賦值 dataToBeSorted[index] = temp; } } return dataToBeSorted; }

雖然功能實現了,但程式碼卻存在著很大的問題,首先在時間複雜度上,我們進行了三次迴圈,其次在空間複雜度上我們使用了temp、index兩個中間變數儲存值,所以這樣寫效率很低。之後我再想,能不能在獲取插入位置的時候,就直接挪位呢?當然看了看網上的寫法[流汗][哈哈],最後程式碼如下

    private static int[] insertionSort(int[] dataToBeSorted) {
        int length = dataToBeSorted.length;
        for(int i=1; i<length; i++) {
            int temp = dataToBeSorted[i];
            int j = i-1;
            // 如果待排序的數字小於前面緊挨的數字
            for(; j>=0 && temp<dataToBeSorted[j]; j--){
                // 前面的數字將後面的數字覆蓋掉,相當於往後挪了一位
                dataToBeSorted[j+1] = dataToBeSorted[j];
            }
            // 如果有序列表有數字挪位了,即需要做插入操作了
            if(j != i-1){
                // 將待排序數字插入到相應位置
                dataToBeSorted[j+1] = temp;
            }
        }
        return dataToBeSorted;
    }

四、總結

當然程式碼編寫並不是固定的,肯定會有很多變形格式,其實我們研究的也是其直接插入的思想和每種寫法的效率問題。如果想要檢視更多演算法基礎,去我的部落格目錄裡檢視吧,因為關於每塊知識點的介紹,部落格單節寫的比較零散,不容易查詢。