常见使用分治法的排序
归并排序
以中间元素为划分,分成两个子问题
伪代码和时间复杂度
快速排序
确定一个数组中不大不小的数x为划分标准,将小于x的元素放到x前面,大于x的元素放到x后面,划分为两个子问题
时间复杂度分析
最好情况
作为划分的元素选取适当,数组被分为长度大致相当的两部分,相当于每次对半分
T
(
n
)
=
2
T
(
n
/
2
)
+
θ
(
n
)
,
T
(
n
)
=
O
(
n
l
g
n
)
T(n)=2T(n/2)+\theta(n),T(n)=O(nlgn)
T(n)=2T(n/2)+θ(n),T(n)=O(nlgn)
最坏情况
划分的元素为最大或最小的元素, T ( n ) = O ( n 2 ) T(n)=O(n^{2}) T(n)=O(n2)
平均情况
随机快速排序
作为划分依据的数是随机产生的
随机快速排序的时间复杂度分析
二叉查找树实际上也是一种快速排序
比较排序问题的下界
比较排序:排序的最终结果中元素的次序依赖于它们之间的比较
决策树:对于每一种排序算法,给定一个数据序列
[
a
1
,
a
2
,
.
.
.
.
]
{[a_1,a_2,....]}
[a1,a2,....],则可根据算法的具体执行过程构造出该排序算法的决策树,输入不同的数据序列则比较次数也不同,决策树的每一片叶子就对应一个确定的数据序列顺序
结论1:任何只用到比较的算法在最坏情况下需要 Ω ( n lg n ) \Omega(n\lg n) Ω(nlgn)次比较,从而使用 Ω ( n lg n ) \Omega(n\lg n) Ω(nlgn)的时间。
最坏情况是指输入的数据序列很差,导致算法执行的比较次数最多,对应到决策树上就是从根节点走到了最深的叶子
证明:决策树的叶子数量是
n
!
n!
n!,决策树的高度至少为
lg
(
n
!
)
\lg(n!)
lg(n!)(当决策树为平衡二叉树时),故最坏情况下算法至少要比较
lg
(
n
!
)
\lg(n!)
lg(n!)次,运用数学知识可得
lg
(
n
!
)
=
Ω
(
n
lg
n
)
\lg(n!)=\Omega(n\lg n)
lg(n!)=Ω(nlgn)
结论2:任何只用到比较的算法在平均情况下需要 Ω ( n lg n ) \Omega(n\lg n) Ω(nlgn) 次比较,从而使用 Ω ( n lg n ) \Omega(n\lg n) Ω(nlgn)的时间。
平均情况指输入的数据序列一般,不是最好也不是最差,算法比较次数取个平均
用根节点到每个叶子节点的路径长度之和除以叶子节点数量来描述其复杂性
证明:可证当二叉树为平衡二叉树时根节点到每个叶子节点的路径长度之和最小,下面计算这个最短路径和
分治法
分治法的时间复杂度
分的时间复杂度+子问题的时间复杂度之和+合并的时间复杂度
大数乘法问题
简单分治算法
将n位二进制转换为两个n/2位二进制
改进分治算法
通过拼凑将子问题划分为3个,将计算两个二进制相乘改良为计算两个二进制数相减降低时间复杂度
棋盘覆盖问题
思路就是将每个
2
k
∗
2
k
2^{k}*2^{k}
2k∗2k的棋盘分为4个小棋盘,再在中间放一个L,保证4个小棋盘中都有一个specific card,这样问题就被划分为了4个子问题
时间复杂度计算:n为大棋盘的面积,则
T
(
n
)
=
4
T
(
n
/
4
)
+
θ
(
1
)
,
T
(
n
)
=
θ
(
n
)
,
n
=
4
k
T(n)=4T(n/4)+\theta(1),T(n)=\theta(n) ,n =4^{k}
T(n)=4T(n/4)+θ(1),T(n)=θ(n),n=4k,
最短距离问题
最小满足条件的数问题(二分)