此條目没有列出任何参考或来源。 (2013年11月10日)維基百科所有的內容都應該可供查證。请协助補充可靠来源以改善这篇条目。无法查证的內容可能會因為異議提出而被移除。
在計算機科學與數學中,一個排序算法(英語:Sorting algorithm)是一種能將一串資料依照特定排序方式排列的算法,排序後的資料即可放在有序陣列。最常用到的排序方式是數值順序以及字典順序。有效的排序算法在一些算法(例如搜尋算法與合併算法(英语:Merge algorithm))中是重要的,如此這些算法才能得到正確解答。排序算法也用在處理文字資料以及產生人類可讀的輸出結果。基本上,排序算法的輸出必須遵守下列兩個原則:
輸出結果為遞增序列(遞增是針對所需的排序順序而言)
輸出結果是原輸入的一種排列、或是重組
雖然排序算法是一個簡單的問題,但是從計算機科學發展以來,在此問題上已經有大量的研究。舉例而言,泡沫排序在1956年就已經被研究。雖然大部分人認為這是一個已經被解決的問題,有用的新算法仍在不斷的被發明。(例子:圖書館排序在2004年被發表)
分類[编辑]
在计算机科学所使用的排序算法通常依以下標準分類:
計算的時間複雜度(最差、平均、和最好性能),依據串列(list)的大小(
n
{\displaystyle n}
)。一般而言,好的性能是
O
(
n
log
n
)
{\displaystyle O(n\log n)}
(大O符号),壞的性能是
O
(
n
2
)
{\displaystyle O(n^{2})}
。對於一個排序理想的性能是
O
(
n
)
{\displaystyle O(n)}
,但平均而言不可能達到。基於比較的排序算法對大多數輸入而言至少需要
O
(
n
log
n
)
{\displaystyle O(n\log n)}
。
内存使用量(以及其他電腦資源的使用)
穩定性:穩定排序算法會讓原本有相等鍵值的紀錄維持相對次序。也就是如果一個排序算法是穩定的,當有兩個相等鍵值的紀錄
R
{\displaystyle R}
和
S
{\displaystyle S}
,且在原本的串列中
R
{\displaystyle R}
出現在
S
{\displaystyle S}
之前,在排序過的串列中
R
{\displaystyle R}
也將會是在
S
{\displaystyle S}
之前。
排序的方法:插入、交換、選擇、合併等等。
穩定性[编辑]
稳定排序纸牌的例子。当纸牌用稳定排序按点值排序的时候,两个5之间必定保持它们最初的次序。在用不稳定排序来排序的时候,两个5可能被按相反次序来排序。
當相等的元素是無法分辨的,比如像是整數,穩定性並不是一個問題。然而,假設以下的數對將要以他們的第一個數字來排序。
(
4
,
1
)
(
3
,
1
)
(
3
,
7
)
(
5
,
6
)
{\displaystyle (4,1)(3,1)(3,7)(5,6)}
在這個狀況下,有可能產生兩種不同的結果,一個是讓相等鍵值的紀錄維持相對的次序,而另外一個則沒有:
(
3
,
1
)
(
3
,
7
)
(
4
,
1
)
(
5
,
6
)
{\displaystyle (3,1)(3,7)(4,1)(5,6)}
(維持次序)
(
3
,
7
)
(
3
,
1
)
(
4
,
1
)
(
5
,
6
)
{\displaystyle (3,7)(3,1)(4,1)(5,6)}
(次序被改變)
不穩定排序算法可能會在相等的鍵值中改變紀錄的相對次序,但是穩定排序算法從來不會如此。不穩定排序算法可以被特別地實作為穩定。作這件事情的一個方式是人工擴充鍵值的比較,如此在其他方面相同鍵值的兩個物件間之比較,(比如上面的比较中加入第二个标准:第二个键值的大小)就會被決定使用在原先資料次序中的條目,當作一個同分決賽。然而,要記住這種次序通常牽涉到額外的空間負擔。
排序算法列表[编辑]
在這個表格中,
n
{\displaystyle n}
是要被排序的紀錄數量以及
k
{\displaystyle k}
是不同鍵值的數量。
穩定的排序[编辑]
冒泡排序(bubble sort)—
O
(
n
2
)
{\displaystyle O(n^{2})}
插入排序(insertion sort)—
O
(
n
2
)
{\displaystyle O(n^{2})}
鸡尾酒排序(cocktail sort)—
O
(
n
2
)
{\displaystyle O(n^{2})}
桶排序(bucket sort)—
O
(
n
)
{\displaystyle O(n)}
;需要
O
(
k
)
{\displaystyle O(k)}
額外空間
计数排序(counting sort)—
O
(
n
+
k
)
{\displaystyle O(n+k)}
;需要
O
(
n
+
k
)
{\displaystyle O(n+k)}
額外空間
归并排序(merge sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
;需要
O
(
n
)
{\displaystyle O(n)}
額外空間
原地归并排序—
O
(
n
log
2
n
)
{\displaystyle O(n\log ^{2}n)}
如果使用最佳的現在版本
二叉排序树排序(binary tree sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
期望时间;
O
(
n
2
)
{\displaystyle O(n^{2})}
最坏时间;需要
O
(
n
)
{\displaystyle O(n)}
額外空間
鸽巢排序(pigeonhole sort)—
O
(
n
+
k
)
{\displaystyle O(n+k)}
;需要
O
(
k
)
{\displaystyle O(k)}
額外空間
基數排序(radix sort)—
O
(
n
k
)
{\displaystyle O(nk)}
;需要
O
(
n
)
{\displaystyle O(n)}
額外空間
侏儒排序(gnome sort)—
O
(
n
2
)
{\displaystyle O(n^{2})}
圖書館排序(library sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
期望时间;
O
(
n
2
)
{\displaystyle O(n^{2})}
最坏时间;需要
(
1
+
ε
)
n
{\displaystyle (1+\varepsilon )n}
額外空間
塊排序(英语:Block sort)(block sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
Tim排序(Timsort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
平均、最坏时间;
O
(
n
)
{\displaystyle O(n)}
最优时间;需要
O
(
n
)
{\displaystyle O(n)}
額外空間;是目前已知最快的排序算法,在Python、Swift、Rust等语言的内置排序功能中被用作默认算法
不穩定的排序[编辑]
選擇排序(selection sort)—
O
(
n
2
)
{\displaystyle O(n^{2})}
希爾排序(shell sort)—
O
(
n
log
2
n
)
{\displaystyle O(n\log ^{2}n)}
如果使用最佳的現在版本
克洛弗排序(Clover sort)—
O
(
n
)
{\displaystyle O(n)}
期望时间,
O
(
n
2
)
{\displaystyle O(n^{2})}
最坏情况[來源請求]
梳排序—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
堆排序(heap sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
平滑排序(英语:Smoothsort)(smooth sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
快速排序(quick sort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
期望時間,
O
(
n
2
)
{\displaystyle O(n^{2})}
最壞情況
內省排序(introsort)—
O
(
n
log
n
)
{\displaystyle O(n\log n)}
耐心排序(patience sort)—
O
(
n
log
n
+
k
)
{\displaystyle O(n\log n+k)}
最坏情況時間,需要額外的
O
(
n
+
k
)
{\displaystyle O(n+k)}
空間,也需要找到最長的遞增子序列(longest increasing subsequence)
不實用的排序[编辑]
Bogo排序—
O
(
n
×
n
!
)
{\displaystyle O(n\times n!)}
,最壞的情況下期望時間為無窮。
Stupid排序—
O
(
n
3
)
{\displaystyle O(n^{3})}
;遞迴版本需要
O
(
n
2
)
{\displaystyle O(n^{2})}
額外記憶體
珠排序(bead sort)—
O
(
n
)
{\displaystyle O(n)}
或
O
(
n
)
{\displaystyle O({\sqrt {n}})}
,但需要特別的硬體
煎餅排序—
O
(
n
)
{\displaystyle O(n)}
,但需要特別的硬體
臭皮匠排序(stooge sort)算法简单,但需要约
n
2.7
{\displaystyle n^{2.7}}
的时间
简要比较[编辑]
名称
数据对象
稳定性
时间复杂度
額外空间复杂度
描述
平均
最坏
冒泡排序
数组
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
1
)
{\displaystyle O(1)}
(无序区,有序区)。從无序区透過交換找出最大元素放到有序区前端。
选择排序
数组
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
1
)
{\displaystyle O(1)}
(有序区,无序区)。在无序区里找一个最小的元素跟在有序区的后面。对数组:比较得多,换得少。
链表
插入排序
数组、链表
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
1
)
{\displaystyle O(1)}
(有序区,无序区)。把无序区的第一个元素插入到有序区的合适的位置。对数组:比较得少,换得多。
堆排序
数组
O
(
n
log
n
)
{\displaystyle O(n\log n)}
O
(
1
)
{\displaystyle O(1)}
(最大堆,有序区)。从堆顶把根卸出来放在有序区之前,再恢复堆。
归并排序
数组
O
(
n
log
2
n
)
{\displaystyle O(n\log ^{2}n)}
O
(
1
)
{\displaystyle O(1)}
把数据分为两段,从两段中逐个选最小的元素移入新数据段的末尾。可从上到下或从下到上进行。
O
(
n
log
n
)
{\displaystyle O(n\log n)}
O
(
n
)
+
O
(
log
n
)
{\displaystyle O(n)+O(\log n)}
如果不是从下到上
链表
O
(
1
)
{\displaystyle O(1)}
快速排序
数组
O
(
n
log
n
)
{\displaystyle O(n\log n)}
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
log
n
)
{\displaystyle O(\log n)}
(小数,基准元素,大数)。 在区间中随机挑选一个元素作基准,将小于基准的元素放在基准之前,大于基准的元素放在基准之后,再分别对小数区与大数区进行排序。
链表
希爾排序
数组
O
(
n
log
2
n
)
{\displaystyle O(n\log ^{2}n)}
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
1
)
{\displaystyle O(1)}
每一輪按照事先決定的間隔進行插入排序,間隔會依次縮小,最後一次一定要是1。
计数排序
数组、链表
O
(
n
+
m
)
{\displaystyle O(n+m)}
O
(
n
+
m
)
{\displaystyle O(n+m)}
统计小于等于该元素值的元素的个数i,于是该元素就放在目标数组的索引i位(i≥0)。
桶排序
数组、链表
O
(
n
)
{\displaystyle O(n)}
O
(
n
2
)
{\displaystyle O(n^{2})}
O
(
m
)
{\displaystyle O(m)}
将值为i的元素放入i号桶,最后依次把桶里的元素倒出来。
基数排序
数组、链表
O
(
k
×
n
)
{\displaystyle O(k\times n)}
O
(
n
2
)
{\displaystyle O(n^{2})}
一种多关键字的排序算法,可用桶排序实现。
均按从小到大排列
k代表数值中的"数位"个数
n代表数据规模
m代表数据的最大值减最小值
参考文献[编辑]
外部链接[编辑]
不同排序算法间的比较(英语) (页面存档备份,存于互联网档案馆)
一些排序算法的C及Pascal实现
可视化排序 (页面存档备份,存于互联网档案馆)
查论编排序算法理论
計算複雜性理論
大O符号
全序关系
数据结构术语列表
原地算法
稳定性
比较排序
自适应排序(英语:Adaptive sort)
排序网络(英语:Sorting network)
整数排序(英语:Integer sorting)
X+Y排序(英语:X + Y sorting)
量子排序(英语:Quantum sort)
交换排序
冒泡排序
鸡尾酒排序
奇偶排序
梳排序
侏儒排序
快速排序
慢速排序
臭皮匠排序
Bogo排序
选择排序
选择排序
堆排序
平滑排序(英语:Smoothsort)
笛卡尔树排序(英语:Cartesian tree sort)
锦标赛排序
圈排序(英语:Cycle sort)
弱堆排序(英语:Weak heap)
插入排序
插入排序
希尔排序
伸展排序
二叉查找树排序
图书馆排序
耐心排序
归并排序
归并排序
梯级归并排序(英语:Cascade merge sort)
振荡归并排序(英语:Oscillating merge sort)
多相归并排序(英语:Polyphase merge sort)
分布排序
美国旗帜排序(英语:American flag sort)
珠排序
桶排序
爆炸排序(英语:Burstsort)
计数排序
比較計數排序
插值排序
鸽巢排序
相邻图排序(英语:Proxmap sort)
基数排序
闪电排序(英语:Flashsort)
并发排序
双调排序器(英语:Bitonic sorter)
Batcher归并网络
两两排序网络(英语:Pairwise sorting network)
混合排序
塊排序(英语:Block sort)
Tim排序
内省排序
Spread排序(英语:Spreadsort)
归并插入排序(英语:Merge-insertion sort)
其他
拓撲排序
煎餅排序
意粉排序(英语:Spaghetti sort)
查论编算法排序比较排序
冒泡排序
选择排序
插入排序
希尔排序
快速排序
归并排序
堆排序
鸡尾酒排序
梳排序
侏儒排序
图书馆排序
内省排序
奇偶排序
线性时间排序
鸽巢排序
基数排序
計數排序
桶排序
并行排序
排序网络(英语:Sorting network)
Batcher归并网络
不实用的
Bogo排序
臭皮匠排序
图
拓撲排序
搜索列表
线性搜索
二分搜索
插值搜尋
树・图
广度优先搜索
最良優先搜索(英语:Best-first search)
均一开销搜索
A*
深度优先搜索
迭代深化深度优先搜索
深度限制搜索(日语:深さ制限探索)
双向搜索
分枝限定法(英语:Branch and bound)
字符串
KMP算法
博耶-穆尔字符串搜索算法
AC自动机算法
拉宾-卡普算法
bitap算法
最短路问题
戴克斯特拉算法
贝尔曼-福特算法
A*搜尋演算法
Floyd-Warshall算法
最小生成树
普林姆算法
克鲁斯克尔演算法
最大流最小割
福特-富尔克森算法
埃德蒙兹-卡普算法
迪尼茨算法
线性规划
单纯形法
卡马卡尔算法(英语:Karmarkar's algorithm)
順序統計量
选择算法
中位数的中位数(英语:Median of medians)
種類
精确算法
近似算法
随机化算法
其他
分治法
动态规划
贪心算法
Category:算法