バブルソート
バブルソートは、ソートアルゴリズムの中でも非常に古典的なソートアルゴリズムで、考え方が比較的シンプルで理解しやすく実装も容易で、一般的に初心者が最初に触れるソートアルゴリズムです。
バブルソーティングと呼ばれる理由は、ソーダのバブリングのように、ソーダのバブリングのように、要素が徐々に上 (最後) に段階的に上昇するためです。
基本的な考え方
1 つずつ比較することにより、各パスは残りの要素の中で最大または最小の要素を決定し、すべての要素が順番どおりになるまで並べ替えます。具体的には, 各ソートでは, 要素はペアで比較されます. 開始位置から開始して, 現在の要素が次の要素と比較されます. 2 つの要素が順番に並んでいる場合は, 無視して 1 つの要素を後方に移動して後方比較を続行します. ,一致しない場合は、最初に要素を交換し、次に要素を 1 つ後方に移動して、このトリップの終わりまで後方比較を続けます。
特徴
平均時間の複雑さ | 最良の場合 | 最悪の場合 | スペースの複雑さ | 並び替え | 安定 |
所定の位置に | 安定させる |
詳細な手順
並べ替える列:
1 | 42 | 65 | 876 | 34 | 656 | 4 |
昇順
最初のパスを並べ替えます。
1 | 42 | 65 | 876 | 34 | 656 | 4 |
1 | 42 | 65 | 876 | 34 | 656 | 4 |
1 | 42 | 65 | 876 | 34 | 656 | 4 |
1 | 42 | 65 | 34 | 876 | 656 | 4 |
1 | 42 | 65 | 34 | 656 | 876 | 4 |
1 | 42 | 65 | 34 | 656 | 4 | 876 |
2 番目の並べ替え:
1 | 42 | 65 | 34 | 656 | 4 | 876 |
1 | 42 | 65 | 34 | 656 | 4 | 876 |
1 | 42 | 34 | 65 | 656 | 4 | 876 |
1 | 42 | 34 | 65 | 656 | 4 | 876 |
1 | 42 | 34 | 65 | 4 | 656 | 876 |
3 番目の並べ替え:
1 | 42 | 34 | 65 | 4 | 656 | 876 |
1 | 34 | 42 | 65 | 4 | 656 | 876 |
1 | 34 | 42 | 65 | 4 | 656 | 876 |
1 | 34 | 42 | 4 | 65 | 656 | 876 |
4 番目の並べ替え:
1 | 34 | 42 | 4 | 65 | 656 | 876 |
1 | 34 | 42 | 4 | 65 | 656 | 876 |
1 | 34 | 4 | 42 | 65 | 656 | 876 |
5 番目の並べ替え:
1 | 34 | 4 | 42 | 65 | 656 | 876 |
1 | 4 | 34 | 42 | 65 | 656 | 876 |
6番目のソート:
1 | 4 | 34 | 42 | 65 | 656 | 876 |
順序シーケンス:
1 | 4 | 34 | 42 | 65 | 656 | 876 |
最適化
実際、バブル ソート アルゴリズムをさらに最適化して、より効率的にすることができます.以下のより極端な例を見てみましょう.
次のように、並べ替えられるシーケンスがあります。これは、既に順序付けられたシーケンスです。
次に、バブルの並べ替えアルゴリズムは、この時点で次の並べ替え操作を実行します。
並べ替えるシーケンスが既に整っている場合でも、バブル並べ替えアルゴリズムは、アルゴリズムの効率を低下させる特定の無用な操作を実行するため、基本的なバブル並べ替えを実行できることが明確にわかります。特定の改善:
要素を交換せずに並べ替え操作を実行すると、並べ替え対象の列が既に並べ替えられていることを意味するため、事前に並べ替え操作を終了できることを記録するフラグを設定します。
高度な最適化
上記のアルゴリズムの最適化により, バブルソートの効率はある程度改善されました. 実際, バブルソートアルゴリズムをさらに最適化することができます. 各ソートプロセスで双方向バブリングを使用できます (最大値と最小値を見つけながら) )、これにより、アルゴリズムの並べ替えの効率がある程度向上します。
ソートする列 | 1 | 42 | 65 | 876 | 34 | 656 | 4 |
最初の旅行 | 1 | 4 | 42 | 65 | 34 | 656 | 876 |
二度目の旅行 | 1 | 4 | 34 | 42 | 65 | 656 | 876 |
三度目の旅 | 1 | 4 | 34 | 42 | 65 | 656 | 876 |
パイソンコード
# 冒泡排序
def bubbleSort(arr):
for i in range(1, len(arr)):
for j in range(0, len(arr)-i): # 每排序一趟就少一个元素需要进行比较(后面的元素已经有序)
#if arr[j] > arr[j + 1]: # 升序
if arr[j] < arr[j + 1]: # 降序
arr[j], arr[j + 1] = arr[j + 1], arr[j]
return arr
if __name__=="__main__":
nums = [1, 42, 65, 876, 34, 656, 4, 6757, 89, 24, 65, 42]
print("start:", nums)
print("冒泡 :", bubbleSort(nums))
Python コードを最適化する
# 冒泡排序
def bubbleSort(arr):
for i in range(1, len(arr)):
flag = False # 设置标志位,判断当前趟次是否有元素交换
for j in range(0, len(arr)-i): # 每排序一趟就少一个元素需要进行比较(后面的元素已经有序)
#if arr[j] > arr[j + 1]: # 升序
if arr[j] < arr[j + 1]: # 降序
arr[j], arr[j + 1] = arr[j + 1], arr[j]
flag = True # 记录发生了交换
if flag==False: # 如果元素未发生交换,说明待排序列已经是有序序列,则提前结束排序
break
return arr
if __name__=="__main__":
nums = [1, 42, 65, 876, 34, 656, 4, 6757, 89, 24, 65, 42]
print("start:", nums)
print("冒泡 :", bubbleSort(nums))
Python コードをさらに最適化する
# 冒泡排序
def bubbleSort(arr):
for i in range(1, len(arr)):
l = 0 # 记录左边元素下标
r = len(nums) - 1 # 记录右边元素下标
flag = False # 设置标志位,判断当前趟次是否有元素交换
# 正向排序最大值
for j in range(l, r):
if arr[j] > arr[j + 1]:
arr[j], arr[j + 1] = arr[j + 1], arr[j]
flag = True
if not flag:
break
# 反向排序最小值
for j in range(r, l, -1):
if arr[j] < arr[j - 1]:
arr[j], arr[j - 1] = arr[j - 1], arr[j]
print(nums)
return arr
if __name__=="__main__":
nums = [1, 42, 65, 876, 34, 656, 4, 6757, 89, 24, 65, 42]
print("start:", nums)
print("冒泡 :", bubbleSort(nums))