1. 程式人生 > >演算法之JS實現氣泡排序的3種方式

演算法之JS實現氣泡排序的3種方式

今天跟同學探討了排序演算法中的氣泡排序,很早之前其實就寫過這個程式碼,但是一直沒有正式的寫到部落格中來,其實氣泡排序是九大排序中最簡單的一個,也是最容易理解的一個排序,好了,廢話不多說,我們先來談一下氣泡排序的思想。
氣泡排序的思想:我們以從小到大排列為例,所謂氣泡排序就是在無序陣列中每執行一趟選出這一趟中最大的數放在最後面,第二趟選出次大的數放在倒數第二位上,以此類推直到完成排序。下來貼程式碼:
第一種方式

var arr=[2,5,4,2,1];
var x;
for(var i=0;i<arr.length-1;i++){
    for(var j=0;j<arr.length-i-1
;j++){ if(arr[j]>arr[j+1]){ x=arr[j+1]; arr[j+1]=arr[j]; arr[j]=x; } } console.log("第"+(i+1)+"趟排序後的陣列是"+arr); } console.log(arr);

執行效果如下:
這裡寫圖片描述

在這裡我們用了兩個迴圈來完成排序,第一個for迴圈是用來控制執行冒泡的趟數,這裡為什麼是arr.length-1,比如我們如果是兩個數排序那麼最多隻需要比較一次就可以了,同樣如果是n個數我們最多隻需冒泡n-1次就可以了,第二個迴圈我們是用來控制每一趟冒泡所需比較的數的個數

,這裡為什麼是arr.length-i-1,因為每冒泡一次就會選出一個最大值,然後下一次冒泡就不用再去比較前一趟所冒泡的最大值了所以長度就會減去i。
第二種方式
主要還是對第一種方式的優化,我們設定一個標誌,如果這一趟發生了交換,則為true,否則為false。如果有一趟沒有發生交換,則說明排序已經完成。程式碼如下:

var arr=[2,5,4,2,1];
var n=arr.length;  
var flag=true;  
while(flag)  
{  
      flag=false;  
      for(var j=1;j<n;j++){ 
            if
(arr[j-1]>arr[j]) { x=arr[j-1]; arr[j-1]=arr[j]; arr[j]=x; flag=true; } } n--; } console.log(arr);

第三種方式
是對前兩種方式的進一步優化,假如陣列長度是20,如果只有前十位是無序排列的,後十位是有序且都大於前十位,所以第一趟遍歷排序的時候發生交換的位置必定小於10,且該位置之後的必定有序,我們只需要排序好該位置之前的就可以,因此我們要來標記這個位置就可以了,程式碼如下:

var arr=[2,5,4,2,1];
var n=arr.length;
var j,k;  
var flag=n;
while(flag>0)  
{  
    k=flag;  
    flag=0;  
    for(j=1;j<k;j++){ 
        if (arr[j - 1] > arr[j])  
        {  
            x=arr[j-1];
            arr[j-1]=arr[j];
            arr[j]=x;
            flag=j;  
        }  
    }  
} 
console.log(arr);

最後需要注意的是氣泡排序最好的時間複雜度為O(n),最壞是O(n^2),平均時間複雜度是O(n^2),且是穩定的排序演算法,氣泡排序雖然說是一種簡單且容易理解的排序,但是畢竟是一種效率低下的排序方法,在資料規模很小時,可以採用。