查找与排序:几种排序的比较

几种排序的比较

排序算法

平均性能

最坏性能

空间复杂度

稳定性

冒泡排序

O(n2)

O(n2)

O(1)

稳定

选择排序

O(n2)

O(n2)

O(1)

不稳定

插入排序

O(n2)

O(n2)

O(1)

稳定

快速排序

O(nLog(n))

O(n2)

O(Log(n))

不稳定

堆排序

O(nLog(n))

O(nLog(n))

O(1)

不稳定

归并排序

O(nLog(n))

O(nLog(n))

O(n)

稳定

从实际的性能来看,快速排序是最快的。
我们看到了这些排序的性能最好的平均也就是O(nLog(n)),有没有办法突破呢?比如到O(n),理论证明这不可能,理论下限就是O(nLog(n))。
不过有特定情况可以提高到O(n),比如计数排序、基数排序和桶排序。

排序算法没有绝对的优劣,只是不同的场景的合适程度不同。最好是做成可替换的,这就要求我们对外的接口统一,我们可以写一个排序工具类,内部使用这些算法,对外提供统一的服务。

class Collections():
    sorter = mergesort.MergeSorter()
    def sort(list):
        Collections.sorter.sort(list)

我们在类Collections里面定义了一个类变量sorter和一个类方法sort(list),不是实例级的,所以客户程序不需要创建Collections的实例,而是直接访问即可。类里面把排序算法默认为归并排序。注意sort()里的写法Collections.sorter.sort(list),直接用的类里面的变量。
客户程序先选择一个算法,传给类,然后调用sort()实现排序。
如:

import mergesort
import quicksort
import collections

if __name__=='__main__':
    a=[38, 27, 43, 3, 9, 82, 10]
    print("before sort:",a)
    #sorter=mergesort.MergeSorter()
    sorter=quicksort.QuickSorter()
    Collections.sorter=sorter
    Collections.sort(a)
    print("after sort:",a)

排序算法是外部传进去的,需要的时候可以替换算法,这是一种策略模式。
自然,要这么写程序,就要求排序算法提供同样的接口,sort(list),统一都是接受一个列表作为参数,统一把排序方法叫做sort()。事实上,我们可以定义这么一个公共的基础类Sorter,然后别的排序算法继承他就可以了。

class Sorter(): #定义基础类
    def sort(self,list):
        Pass

class MergeSorter(sorter.Sorter): #继承

 

上一篇:《算法图解》- 快速排序


下一篇:Nlog-File输出配置