數據結構與算法系列——排序(8.1)_冒泡排序

1. 工做原理(定義)

  核心思想:冒泡排序是一種典型的 交換排序 ,經過比較相鄰元素大小來決定是否交換位置html

  冒泡排序的思想:不停地比較相鄰的兩個記錄,若是相鄰的兩個記錄的次序是反序則交換,直到全部的記錄都已經排好序了(使關鍵字最小或最大的記錄如氣泡通常逐漸往上「漂浮」直至「水面」,因此叫冒泡排序)。git

2. 算法步驟

  1. 比較相鄰的元素。若是第一個比第二個大,就交換他們兩個。github

  2. 對每一對相鄰元素做一樣的工做,從開始第一對到結尾的最後一對。這步作完後,最後的元素會是最大的數。算法

  3. 針對全部的元素重複以上的步驟,除了最後一個。數據結構

  4. 持續每次對愈來愈少的元素重複上面的步驟,直到沒有任何一對數字須要比較。

  

 

3. 動畫演示

4. 性能分析

1. 時間複雜度

  (1)順序排列時,冒泡排序總的比較次數爲n-1(比較一輪後就跳出循環),移動次數爲0; 
  (2)逆序排序時,冒泡排序總的比較次數爲n(n-1)/2,移動次數爲n(n-1)/2次; 
  (3)當原始序列雜亂無序時,平均時間複雜度爲O(n^2)。函數

  若文件的初始狀態是正序的,一趟掃描便可完成排序。所需的關鍵字比較次數   和記錄移動次數   均達到最小值:   ,   。因此,冒泡排序最好的時間複雜度爲   。
  若初始文件是反序的,須要進行  趟排序。每趟排序要進行  次關鍵字的比較(1≤i≤n-1),且每次比較都必須移動記錄三次來達到交換記錄位置。在這種狀況下,比較和移動次數均達到最大值:  。冒泡排序的最壞時間複雜度爲  。綜上,所以冒泡排序總的平均時間複雜度爲  

2. 空間複雜度

  冒泡排序排序過程當中,Swap函數須要一個臨時變量temp進行兩兩交換,所須要的額外空間爲1,所以空間複雜度爲O(1)。性能

3. 算法穩定性 

  冒泡排序在排序過程當中,元素兩兩交換時,相同元素的先後順序並無改變,因此冒泡排序是一種穩定排序算法。學習

4. 初始順序狀態

  1. 比較次數:
  2. 移動次數:
  3. 複雜度:    
  4. 排序趟數:

5. 歸位

  能歸位,每一趟排序有一個元素歸位。動畫

6. 優勢

6. 改進算法

  1. 對因而否已是有序排列進行判斷;
  2. 對已經排序好的元素不參與重複的比較。

7. 具體代碼

public int[] bubbleSort1(int[] sourceArray) throws Exception { // 對 arr 進行拷貝,不改變參數內容
    int[] arr = Arrays.copyOf(sourceArray, sourceArray.length); for (int i = 1; i < arr.length; i++) { for (int j = 0; j < arr.length - i; j++) { if (arr[j] > arr[j + 1]) {//等於就不交換,保證了穩定性 int tmp = arr[j]; arr[j] = arr[j + 1]; arr[j + 1] = tmp; } } } return arr; } /* *設置一個標識,若是在某一趟遍歷中沒有發生交換,說明排序已經完成,即算法完成 */
public int[] bubbleSort2(int[] sourceArray) throws Exception { // 對 arr 進行拷貝,不改變參數內容
    int[] arr = Arrays.copyOf(sourceArray, sourceArray.length); for (int i = 1; i < arr.length; i++) { // 設定一個標記,若爲true,則表示這次循環沒有進行交換,也就是待排序列已經有序,排序已經完成。
        boolean flagChange = true; for (int j = 0; j < arr.length - i; j++) { if (arr[j] > arr[j + 1]) { int tmp = arr[j]; arr[j] = arr[j + 1]; arr[j + 1] = tmp; flagChange = false; } } if (flagChange) { break; } } return arr; } // set flag to indicate what next step should begin from
public int[] bubbleSort3(int[] sourceArray) { // 對 arr 進行拷貝,不改變參數內容
    int[] arr = Arrays.copyOf(sourceArray, sourceArray.length); int tmpNextPosition = sourceArray.length-1; for (int i = 1; i < arr.length; i++) { // 設定一個標記,若爲true,則表示這次循環沒有進行交換,也就是待排序列已經有序,排序已經完成。
        boolean flagChange = true; int nextPosition = tmpNextPosition; for (int j = 0; j < nextPosition; j++) { if (arr[j] > arr[j + 1]) { int tmp = arr[j]; arr[j] = arr[j + 1]; arr[j + 1] = tmp; flagChange = false; tmpNextPosition = j; } } if (flagChange) { break; } } return arr; }

 

8. 參考網址

  1. 數據結構基礎學習筆記目錄
  2. 75-交換排序——冒泡排序
  3. 排序算法系列之冒泡排序
  4. https://visualgo.net/en/sorting
  5. https://www.runoob.com/w3cnote/bubble-sort.html
  6. https://github.com/hustcc/JS-Sorting-Algorithm
  7. 冒泡排序
相關文章
相關標籤/搜索