评估Divide and Conquer算法时间复杂度的几种策略
算法导论的第四章对于divide-conquer进行了阐述, 感觉这本书特别在,实际给出的例子并不多,更多其实是一些偏向数学性质的分析, 最重要的是告诉你该类算法分析的一般性策略。
估计
首先是估计算法的时间复杂度,这里我感觉大多数情况下该类算法的时间复杂度可以由两种策略来完成。
master method
这种方式简单, 准确, 个人认为一般能用这种尽量使用这种。
对于常数 a >= 1, b > 1, T(n) = a T ( n / b ) + f(n), 也就是说算法T对于规模为n的问题, 花费f(n)的时间复杂度可以将之化简为a个规模为n/b的问题, 此时有如下性质 :
- 如果f(n) = O(n ^ (log b (a - ε))), 且ε > 0, 那么T(n)的时间复杂度是θ(n ^ (log b (a))), 例如 T(n) = 3T(n / 2) + n的时间复杂度就是θ(n ^ (log 2 (3))).
- 如果f(n) = θ(n ^ (log b (a))), 那么T(n)的时间复杂度是θ(n^(log b (a)) * log 2 (n)), 例如归并排序, T(n) = 2T(n / 2) + n的时间复杂度就是θ(n * log2 (n)).
- 如果f(n) = Ω(n ^ (log b (a + ε))), 且ε > 0, a * f(n / b) <= c * f(n) 对于 c < 1 and n 足够大都成立, 那么T(n)的时间复杂度是θ(f(n)). 例如 T(n) = T(n / 5) + n的时间复杂度就是θ(n).
递归树
这种方式使用面更广, 而且更加直接, 但是需要对算法本身以及其过程有较为清晰的了解, 同时需要花费更长的时间。
下面我给出几种情况, 并画出递归树。
典型的例子是归并排序, T(n) = 2 T(n / 2) + n
n
n/2 n/2
n/4 n/4 n/4 n/4
...
n个1
根据算法本身分析, 我们知道每层递归将导致算法的规模下降到原来的一半也就是说, 递归树的高度应该是(log 2 (n)), 另一方面, 对于树的每一层,总的合并所需要的时间是n, 所以可以估算出该算法的时间复杂度是θ(n * log2 (n)).
这里给出一个不能用master method的例子, 比如 T(n) = 2 T (n - 1) + n
n
n-1 n-1
n-2 n-2 n-2 n-2
...
我们很容易分析得到的结论是该递归树的高度为n, 并且在最底层有2^n个元素, 除去最后一层的base case, 之前应该是n + n - 1 + n - 2 + ... + k (假设n = k是base case), 大概估算一下这个算法的时间复杂度应该是θ(2 ^ n + n ^ 2), 化简之后也就是θ(2 ^ n).
证明
然后估计之后是证明, 总体来讲证明就是用substitution method, 也就是说先假设你猜想成立, 然后反过来推导出要证明的目标不等式.
假设对于归并排序有O(nlogn), 那么就有 T(n) <= c * nlog(n), 替换之后就是T (n) <= 2 * c * (n / 2 * log (n / 2)) + n 化简一波就是 T (n)<= c * nlogn + (1- c)n, 那么因为我们要证明的目标不等式是 T(n) <= cnlogn, 此时只需要 1 - c <= 0即可, 所以存在c(实际上c只要在0[0, 1]之间都可). 基本的思路就是这样, 其实这就是数学归纳法的最后一步, 也就是说你假设n-1的时候成立然后证明出来对于n也成立.
这一章的话大概就是这样.
评估Divide and Conquer算法时间复杂度的几种策略的更多相关文章
- 算法与数据结构基础 - 分治法(Divide and Conquer)
分治法基础 分治法(Divide and Conquer)顾名思义,思想核心是将问题拆分为子问题,对子问题求解.最终合并结果,分治法用伪代码表示如下: function f(input x size ...
- 算法上机题目mergesort,priority queue,Quicksort,divide and conquer
1.Implement exercise 2.3-7. 2. Implement priority queue. 3. Implement Quicksort and answer the follo ...
- 【LeetCode】分治法 divide and conquer (共17题)
链接:https://leetcode.com/tag/divide-and-conquer/ [4]Median of Two Sorted Arrays [23]Merge k Sorted Li ...
- The Divide and Conquer Approach - 归并排序
The divide and conquer approach - 归并排序 归并排序所应用的理论思想叫做分治法. 分治法的思想是: 将问题分解为若干个规模较小,并且类似于原问题的子问题, 然后递归( ...
- [LeetCode] 系统刷题4_Binary Tree & Divide and Conquer
参考[LeetCode] questions conlusion_InOrder, PreOrder, PostOrder traversal 可以对binary tree进行遍历. 此处说明Divi ...
- 深入浅出数据结构C语言班(11)——简要介绍算法时间复杂度
在接下来的数据结构博文中,我们将会开始接触到一些算法,也就是"解决某个问题的方法",而解决同一个问题总是会存在不同的算法,所以我们需要在不同的算法之中做出抉择,而做出抉择的根据往往 ...
- [LeetCode] 236. Lowest Common Ancestor of a Binary Tree_ Medium tag: DFS, Divide and conquer
Given a binary tree, find the lowest common ancestor (LCA) of two given nodes in the tree. According ...
- 新发现:排序算法时间复杂度只有O(3n),命名为"wgw"排序法
思路:首先在待排序数组i[]中找出最大的值,以(最大值+1)的大小创建一个空数组kk[],然后遍历待排序数组i[]中的值n,其值n对应数组kk[]中的第n个元素加1.最后再把数组kk[]排好序的值赋回 ...
- [LeetCode] 124. Binary Tree Maximum Path Sum_ Hard tag: DFS recursive, Divide and conquer
Given a non-empty binary tree, find the maximum path sum. For this problem, a path is defined as any ...
随机推荐
- MyEclipse Spring 学习总结三 SpringMVC 表单处理
SpringMVC 表单处理的项目结构如下图所示: Student.java 文件 public class Student { private Integer age; private String ...
- Apache Shiro 使用手册(三)Shiro 授权
授权即访问控制,它将判断用户在应用程序中对资源是否拥有相应的访问权限. 如,判断一个用户有查看页面的权限,编辑数据的权限,拥有某一按钮的权限,以及是否拥有打印的权限等等. 一.授权的三要素 授权有着三 ...
- 微分方程——基本概念和常微分方程的发展史
1.2 基本概念和常微分方程的发展史 自变量.未知函数均为实值的微分方程称为实值微分方程:未知函数取复值或变量及未知函数均取复值时称为复值微分方程.若无特别声明,以下均指实变量的实值微分方程. 1.2 ...
- ORACLE创建表之前判断表是否存在与SQL Server 对比使用
在SQL Server 数据库中,我们在创建表之前删除表,有if exit()这样的语句,但是在oracle中却没有.如果直接使用drop table那么如果表不存在会报错,导致后续语句无法运行.因此 ...
- 利用Gson和SharePreference存储结构化数据
问题的导入 Android互联网产品通常会有很多的结构化数据需要保存,比如对于登录这个流程,通常会保存诸如username.profile_pic.access_token等等之类的数据,这些数据可以 ...
- 如何删除控制文件中过去rman备份到磁带的备份集
问题描述: 早上做数据库巡检,发现FRA(flash recovery area)空间使用率达到66%,是平时的两倍.由于库不大,备份策略是本地磁盘备份,每天一全备,REDUNDANCY 1 ,备份完 ...
- windows8.1+centos7双系统(装完centos后无win8引导)
原先系统为windows8.1后来装上centos7后无win8系统引导, 打开电脑进入引导界面按C 进入grub界面 输入“cat (hd0,” 按tab可查看到windows8 地址为“hd0, ...
- nodejs http 请求延时的处理方法(防止程序崩溃)
有时候因为接口没开,或者其他原因,导致http.request 请求延时,一直耗费资源不说,还会导致程序报错崩溃,延时处理其实也是一种错误处理. 直接上代码: var APIGET = functio ...
- lintcode-【简单题】链表求和
题目: 你有两个用链表代表的整数,其中每个节点包含一个数字.数字存储按照在原来整数中相反的顺序,使得第一个数字位于链表的开头.写出一个函数将两个整数相加,用链表形式返回和. 样例: 给出两个链表 3- ...
- js进度条实现
1.先设置CSS样式(可自定义) /*#region 进度条 */ .progbar { background-color: #e1e1e1; width:auto; color: #222; hei ...