(3更)算法总结

贪心算法

Q:什么是贪心算法?

A:不管最后怎么样,先获得当前的最优解。所以贪心算法最后得到的解并不一定是最优解

       例子:一个袋子可以装4斤水果,现在有3斤苹果,2斤草莓,2斤葡萄,贪心算法就会直接先把苹果装进去,其实最优的是装2斤草莓2斤葡萄!

相关应用:

Prim算法、Kruskal算法、喷泉问题、会场问题、过河问题、01背包问题

什么是Prim算法?

从任意一个顶点开始,寻找与当前点最近的点,将两顶点的边加入到树中,构造出权值最小的生成树。

详细来说:

1.将图的所有点放到集合V内,从中选出任意一点作为点集U的起始点{v1}

2.寻找V—U中与U中的点可连接的权值最小的点,将点加入U中,从V—U中删去(注意此时不能形成环)

(实际算法中会引入一个辅助数组,记录从U到V—U的最小代价的边。所以这个辅助数组是实时更新的,例如:此时U{v1,v3},那么在v3寻找关连边的点时,碰到了与v1也可以关联的点,并且v3与该点的权值小于v1,那么更新辅助数组)

3.重复2操作,直到V—U中的点为空,那么U中的点构成的树就是最小生成树

什么是Kruskal算法?

其实它也是构成最小生成树的算法,但是和Prim不同的是,Prim是根据点求出最小生成树,而Kruskal是根据边求出最小生成树。所以在边多的情况下,尽量不用Kruskal算法。

详细来说:

1.先将所有边按照权值由大到小进行排列

2.按照顺序选择边,如果该边的两个节点不属于同一个集合,那就将它合并,如果属于同一个集合,就舍弃此边,再寻找下一边,直到所有的节点都属于同一个集合。

那么这里发现一个问题,我们要如何将节点合并呢?

这里就出现了一个并查集方法。

什么是并查集?

1.查询元素a与b是否处于同一个集合内

2.合并元素ab为一组

并查集结构用树来实现,如下图,当我们要看两个元素是否相等,那么只需要看它们的根节点是否相等,如果相等就属于同一集合。而合并时只需要将两个根节点相连就可以。


简单的并查集算法会发现有一个巨大的缺点:极有可能退化成线性结构

那么这时候就需要用“路径压缩”和“按秩合并”阻止它的退化

什么叫路径压缩?

将原本与根节点间接相连的点变为与根节点直接相连,如下图

什么叫按秩合并(unit)?

对于每一棵树,记录它的高度。每次合并树时,将矮的树挂在高的树下



喷泉问题(一):


作法:圆的内切正方形的边长为草坪的宽

喷泉问题(二):


作法:1.舍去半径小于草坪宽二分之一的圆,

           2.记录其他圆形成的矩形边界,排序符合的矩形

           3.判断第一个矩形的左边界是否大于零,大于零则不存在符合喷泉装置将草坪润湿

           4.遍历矩形右边界,直到右边界大于矩形长度,结束遍历,输出count值


会场安排问题:


作法:1.vector存下所有活动,将活动按结束时间的近远进行排序

           2.变量a保存vector的大小。

           3.看第一个活动结束时间是否大于其他活动的开始时间,如果大于某一活动,a减1,否则查看该活动的结束时间是否大于其他活动的开始时间(如果上一个活动在t时间内结束,那么下一个活动应该在t+1时间开始)


过河问题:


作法:1.当N==1或N==2,直接过河

           2.当N==3,最快与次快先过河,最快的拿着手电筒返回,再与最慢的一起过河

           3.当N>=4,a[0]为最快的人过河时间,a[1]为次快,a[n-1]为最慢的人过河,a[n-2]为次慢。通过N=3,4,归纳总结可知,过河时间存在两个方案

            方案一:a[0]与a[n-1]先过河,a[0]返回再与a[n-2]过河

            方案二:a[0]与a[1]先过河,a[0]返回,a[n-1]与a[n-2]过河,a[1]返回,a[0]与a[1]过河

            过河时间的方案的差异只与a[0],a[1],a[n-2]有关,当a[0]+a[n-2]-2a[1]>0时选择方案一,小于0选择方案二,每执行一次就减少两人,直到人小于4为止


01背包问题:


作法:将物品价值最大的先放入背包



动态规划(大事化小)

Q:动态规划的特征是什么?

A:最优子结构、无后效性

      最优子结构:当前的最优状态可以由某个或某些状态直接得到

      无后效性:不管之前这个状态是如何得到的(比如迷宫问题,我们在记录当前路线的时候会影响到下一步路线的选择,这就是有后效性。os:搜索解决迷宫问题,搜索:每个阶段的最优状态都是由之前所有状态组合得到的。)

动态规划的实质:

1.分析问题,构造状态转移方程(通过最优子结构推导得出),注意边界问题

2.以空间时间(什么是空间复杂性?支持计算所要用到的存储状态最多有多少

                            什么是时间复杂性?从初始状态到最终状态走了多少步)


动态规划的解题步骤:

1.确定子问题。(确定哪些变量随着问题规模的变小而变小)

2.确定状态。(给子问题限定状态)

3.推导出状态转移方程(根据子问题进行推导)

4.确定边界

5.确定实现方式

6.确定优化方法(有时候会发现当执行到步骤5时就会返回步骤1继续执行,中间就会有很多重复部分,所以这时候就要采用:降维问题、优先队列、四边形不等式优化等)


相关题目:

有一座高度是10级台阶的楼梯,从下往上走,每跨一步只能向上1级或者2级台阶。要求用程序来求出一共有多少种走法。

    1.假设只差最后一步就可以踏上第10级台阶,那么此时有两种方法,一个是站在第九级台阶往上走一步,另一个是站在第八级台阶往上走两步。

    2.假设走到九级有X种方法,走到八级有Y种方法,那么走到十级就是X+Y,所以这里可以得出递推方程:F(n)=F(n-1)+F(n-2)

    其实当我们推导出一个递推的方程F(n)=F(n-1)+F(n-2),如果直接用递推方式去解决,那么会存在很多重复的计算(当我们求F(n),要得到F(n-1),F(n-2)的值,要得到F(n-1),就要得到F(n-2),F(n-3)的值,可以看出F(n-2)计算了两次)。

    如果我们将F(n-1),F(n-2)存储起来,那么求解F(n)就只需要一步加法,此时时间复杂性降低,空间复杂性增加,这就叫做空间换时间。(这就叫做“备忘录算法”,备忘录算法保留所有子状态,它与动态规划的最大的不同就是它是“自顶向下”,动态规划是“自底向上”)

    再思考一下,能不能把空间复杂性缩小,那么我们自底向上,用迭代方式求出结果,台阶的走法数量由前两个台阶数量相加而成。所以我们根本不需要把所有的子状态都记录,只需要记录当前状态的前两个状态,就可以求出当前状态。这就是动态规划的实现


最长公共子序列问题(LCS):

解题思路:

设A=“a0,a1.....am-1”,B="b0,b1...bn-1",Z="z0,z1...zk-1",Z为AB的最长公共子数列

1.当am-1==bn-1时,则查找"a0,a1...am-2"与"b0,b1...bn-2"的最长公共子序列

2.当am-1!=bn-1时,则在"a0,a1,....am-2"与"b0,b1..bn-1" 和 "a0,a1,....am-1"与"b0,b1..bn-2"中找到最长的公共子序列


最长递增子序列问题(LIS):

解题思路:

1.因为是查找子序列而不是子串,所以递增序列不需要连续。

2.外层遍历给定数组,内层遍历外层 i之前的数

    那么我们需要判断 a[ j ] < a[ i ] (以及Dp( i ) < Dp( j ) + 1),就可以给子序列的长度加1,所以得出状态转移方程为 Dp( i ) = Dp( j ) + 1


优化上面的算法:

    将数一个一个插入队列中,如果发现当前数大于队尾数,那么就插在队尾,反之就用二分法查找大于当前数的最小值的位置,替换为当前数。


01背包问题:

解题思路:

设B(i)为背包价值,W(i)为物品重量,V[i]为物品价值,capacity为背包可以放的最大容量

1.物品有放和不放两种状态,那么如何判断放进去的东西能使利益最大化呢?

2.当背包当前容量比物品重量还小时,不能再放进东西,这时背包的价值与前面B(i-1)价值相等

3.当背包容量可以再放进物品,但装了也不一定达到当前的最优价值,所以在装与不装之间选择最优的一个,

装进物品:

    就是取{w1,w2,w3....wi-1}的物品,装入体积为当前背包剩余容量减去要装进的物品wi容量,所得到的最大值再加上要wi的价值。

不装入:

    就是取{w1,w2,w3....wi-1,wi}的物品,装入当前背包容量,所得的最大价值

从上面两种找出最优价值即可,所以装不装只第i-1个物品有关。


完全背包问题:

解题思路:

1.这个时候和01背包就不一样了,01背包是有取或者不取的策略,而这里则是取0种、取1种...等策略

2.解题思路与01背包略微相似

   但是就是在背包容量可以放下东西时不同,这时候我们也需要在装与不装之间选择

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,884评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,347评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,435评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,509评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,611评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,837评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,987评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,730评论 0 267
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,194评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,525评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,664评论 1 340
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,334评论 4 330
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,944评论 3 313
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,764评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,997评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,389评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,554评论 2 349

推荐阅读更多精彩内容