国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > Java > 正文

Java實現冒泡排序算法及對其的簡單優化示例

2019-11-26 14:23:13
字體:
來源:轉載
供稿:網友

原理

冒泡排序大概是所有程序員都會用的算法,也是最熟悉的算法之一。
它的思路并不復雜:
設現在要給數組arr[]排序,它有n個元素。
1.如果n=1:顯然不用排了。(實際上這個討論似乎沒什么必要)
2.如果n>1:
(1)我們從第一個元素開始,把每兩個相鄰元素進行比較,如果前面的元素比后面的大,那么在最后的結果里面前者肯定排在后面。所以,我們把這兩個元素交換。然后進行下兩個相鄰的元素的比較。如此直到最后一對元素比較完畢,則第一輪排序完成。可以肯定,最后一個元素一定是數組中最大的(因為每次都把相對大的放到后面了)。
(2)重復上述過程,這次我們無需考慮最后一個,因為它已經排好了。
(3)如此直到只剩一個元素,這個元素一定是最小的,那么我們的排序可以結束了。顯然,進行了n-1次排序。
上述過程中,每次(或者叫做“輪”)排序都會有一個數從某個位置慢慢“浮動”到最終的位置(畫個示意圖,把數組畫成豎直的就可以看出來),就像冒泡一樣,所以,它被稱為“冒泡排序法”。

代碼實現:

public class BubbleSort{   public static void main(String[] args){     int score[] = {67, 69, 75, 87, 89, 90, 99, 100};     for (int i = 0; i < score.length -1; i++){  //最多做n-1趟排序       for(int j = 0 ;j < score.length - i - 1; j++){  //對當前無序區間score[0......length-i-1]進行排序(j的范圍很關鍵,這個范圍實在逐步縮小的)         if(score[j] < score[j + 1]){  //把小的值交換到后面           int temp = score[j];           score[j] = score[j + 1];           score[j + 1] = temp;         }       }             System.out.print("第" + (i + 1) + "次排序結果:");       for(int a = 0; a < score.length; a++){         System.out.print(score[a] + "/t");       }       System.out.println("");     }       System.out.print("最終排序結果:");       for(int a = 0; a < score.length; a++){         System.out.print(score[a] + "/t");     }   } }

 
算法性能/復雜度
我們忽略掉循環變量自增和初始化的時間。先分析算法的比較次數。容易看出,上面這種未經任何改進的冒泡排序無論輸入數據如何都會進行n-1輪排序,而每輪排序需要比較的次數從n-1遞減到0。那么,總的比較次數即是 (n-1)+(n-2)+...+2+1 = (n-1)n/2≈(n^2)/2。(由于不知道這里如何打出平方,這里,我用n^2代表平方,下同)
再來看下賦值次數。這里的賦值是指其中的交換操作,對于上述代碼,1次交換等于三次賦值。由于并非每次都必須交換,因此,賦值操作的次數與輸入數據有關。最佳情況(best case)下,即一開始就是有序的情況下,賦值次數為0。 而最壞情況(worst case)下,賦值次數為(n-1)n/2。假設輸入數據平均(或者說“完全隨機”)分布,那么大約有交換次數為比較次數的一半。由上面的結果,可以得到平均情況(average case)下,賦值次數為 3/2 * (n^2)/2 = 3/4*(n^2).
綜上,無論在何種情況下,冒泡排序空間復雜度(額外空間)總是O(1)。

改進
在數據完全有序的時候展現出最優時間復雜度,為O(n)。其他情況下,幾乎總是O(n^2)。因此,算法在數據基本有序的情況下,性能最好。
但是,上面的代碼怎么可能出現O(n)復雜度呢?實際上,因為上面注重的是基本思路,因此只是最簡單情況,要使算法在最佳情況下有O(n)復雜度,需要做一些改進,改進后的代碼為:

public static void bubbleSort(int[] arr) {  int temp = 0;  boolean swap;  for (int i = arr.length - 1; i > 0; --i) { // 每次需要排序的長度    swap=false;    for (int j = 0; j < i; ++j) { // 從第一個元素到第i個元素      if (arr[j] > arr[j + 1]) {        temp = arr[j];        arr[j] = arr[j + 1];        arr[j + 1] = temp;        swap=true;      }    }//loop j    if (swap==false){      break;    }  }//loop i}// method bubbleSort

實際上,由于在大量數據的情況下幾乎不使用冒泡排序,而使用小數據的時候增加的布爾變量反而會造成額外的開銷。所以個人認為上面改進后的算法只是純理論的,通常,冒泡排序就寫前面一種就行了。

算法穩定性
容易看出,在相鄰元素相等時,我們并不需要交換它們的位置,所以,冒泡排序是穩定排序。

算法適用場景
冒泡排序思路簡單,代碼也簡單,特別適合小數據的排序。但是,由于算法復雜度較高,在數據量大的時候不適合使用。如果一定要在較多數據的時候使用,最好對算法加以改進,例如選擇排序法。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 扎兰屯市| 胶州市| 梁平县| 天台县| 石门县| 台江县| 大同市| 伊宁县| 绵阳市| 潢川县| 台湾省| 无棣县| 南充市| 密山市| 龙岩市| 逊克县| 伊川县| 上栗县| 晋中市| 榆中县| 海口市| 灌阳县| 万荣县| 陆河县| 军事| 德兴市| 巩留县| 龙江县| 江油市| 合山市| 弋阳县| 仪征市| 滕州市| 正镶白旗| 万宁市| 牡丹江市| 山丹县| 瑞昌市| 兰溪市| 萝北县| 涞水县|