经典的三种排序算法

本文详细介绍了归并排序、堆排序及快速排序三种重要的排序算法。分析了每种算法的工作原理、实现过程及其时间复杂度,并对比了它们之间的优劣。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

归并排序:

归并排序。可以说分治策略用在了排序问题上。
我们每次将数组分成两半。递归的排序这两半。然后用线性时间将其合并起来。变成一个完整的有序数组。

复杂度分析:
T(n)=2T(n2)+O(n)

显然最多展开log2n层。所以总时间复杂度:O(nlogn)

堆排序:

如果不知道堆这个数据结构的同学。可以自行学习。(百度一大把)
通过不停到调整堆来做到排序。
每次将堆顶最小元素与堆最中后一个元素交换。类似于把最后一个元素从新入堆。
这一步从新调整耗费O(log2n)

排序n个元素复杂度:O(nlogn)

快速排序

正如其名。快速排序。当然是非常快的。

也是最重要。最需要学习的排序。

快速排序为何如此之快?
快速排序与归并排序类似。
不同的是:快速排序是先划分。不需要合并。
归并排序最慢的部分。就是需要把数组归并到一个辅助数组中。在把排序到辅助数组中的元素从新拷贝到原来数组对应位置。

快速排序不同:

最经典的快速排序是随机的选择一个数列中的元素a

然后将这n个元素的序列划分为:

[a] a [a]

具体实现技巧在于。

我们随机的选择a=A[i].

A[i]A[0]交换位置。

t=0,k=n1

我们认为:A[0..t1]所有元素小于等于a

我们认为:A[k+1..n1]所有元素大于等于a

开始时, aA[t] 位置。

循环:检查A[k]是否小于A[t]

如果不是k=k1,继续检查。直到k等于t.此时划分完成。
如果是 : 将A[k]归入小于等于a的集合。即:交换A[t],A[k]

检查A[k]是否小于A[t]

如果不是, t=t+1.直到k等于t,划分结束。
如果是。交换A[k],A[t],返回循环的位置。

通过这样的划分。我们将序列划分成了不大于a的部分和不小于a的部分。

a现在的位置为mid.显然。a的位置不需要改变了。

我们只需要递归的排序:
sort(0,mid1)sort(mid+1,n1)

快速排序的效率难免有些许不稳定。因为它的速度与它的划分是否得当有关。
但实践表明。总是出现坏的情况的划分是几乎不可能能的。快速排序的速度要比归并排序和堆排序都要快。
我们计算一下平均意义下的快速排序的效率:

T(n)=1nk=1n(T(nk)+T(k1))+cn=2nk=0n1T(k)+cn

cn是划分n个元素时需要的时间。且a不需要排序。所以T(k1)+T(nk)

所以:
nT(n)=2k=0n1T(n)+cn2

n1时:
(n1)T(n1)=2k=1n2T(k)+c(n1)2

两式子做差有:
nT(n)(n1)T(n1)=2T(n1)+2cn1nT(n)=(n+1)T(n)+2cn1

哇,两边除去n(n+1)

T(n)n+1=T(n1)n+2cn+11n(n+1)

令:
S(n)=T(n)n+1 , n0

所以:
S(n)=S(n1)+2cn+11n(n+1)

所以:
S(n)=k=1n2ck+1k=1n1k(k+1)

啊哈。有经验的人必然会发现:
1k(k+1)=1k1k+1

所以:
S(n)=k=1n2ck+1k=1n1k+k=1n1k+1=2ck=2n+11knn+1

也就是说:
T(n)n+1=2ck=2n+11knn+1T(n)=2c(n+1)k=2n1k+1n

即:
T(n)=2cnHn+Hn(2c+1)n2c+1

其中
Hn=11+12+13+...+1n

HnO(n11x dx)=O(logen)

所以:
T(n)=O(nlogn)

因为排序思想都比较简单。所以也就不再给出关于这三种排序的代码实现了.

在很多复杂度分析和算法思想中都可以找到这三种算法的影子。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值