> 文章列表 > 力扣55. 跳跃游戏贪心算法

力扣55. 跳跃游戏贪心算法

力扣55. 跳跃游戏贪心算法

给定一个非负整数数组 nums ,你最初位于数组的 第一个下标 。

数组中的每个元素代表你在该位置可以跳跃的最大长度。

判断你是否能够到达最后一个下标。

 

 代码:

class Solution {public boolean canJump(int[] nums) {int cov=0;if (nums.length==1 ){return true;}else{for(int i=0;i<=nums.length-1;i++){if(i<=cov){cov=Math.max(cov,i+nums[i]);if(cov>=nums.length-1){return true;}}} return false;}
}}

方法一:贪心
我们可以用贪心的方法解决这个问题。依次遍历数组中的每一个位置,并实时维护 最远可以到达的位置。对于当前遍历到的位置 xxx,如果它在 最远可以到达的位置 的范围内,那么我们就可以从起点通过若干次跳跃到达该位置,因此我们可以用 x+nums[x]x + \\textit{nums}[x]x+nums[x] 更新 最远可以到达的位置。

在遍历的过程中,如果 最远可以到达的位置 大于等于数组中的最后一个位置,那就说明最后一个位置可达,我们就可以直接返回 True 作为答案。反之,如果在遍历结束后,最后一个位置仍然不可达,我们就返回 False 作为答案。

以题目中的示例一

[2, 3, 1, 1, 4]
为例:

我们一开始在位置 000,可以跳跃的最大长度为 222,因此最远可以到达的位置被更新为 222;

我们遍历到位置 111,由于 1≤21 \\leq 21≤2,因此位置 111 可达。我们用 111 加上它可以跳跃的最大长度 333,将最远可以到达的位置更新为 444。由于 444 大于等于最后一个位置 444,因此我们直接返回 True。

我们再来看看题目中的示例二

[3, 2, 1, 0, 4]
我们一开始在位置 000,可以跳跃的最大长度为 333,因此最远可以到达的位置被更新为 333;

我们遍历到位置 111,由于 1≤31 \\leq 31≤3,因此位置 111 可达,加上它可以跳跃的最大长度 222 得到 333,没有超过最远可以到达的位置;

位置 222、位置 333 同理,最远可以到达的位置不会被更新;

我们遍历到位置 444,由于 4>34 > 34>3,因此位置 444 不可达,我们也就不考虑它可以跳跃的最大长度了。

=========================

贪心算法总是作出在当前看来最好的选择。即贪心算法并不从整体最优考虑,它所作出的选择只是在某种意义上的局部最优选择,不一定达到全局最优。
    当一个问题动具有最优子结构性质时,可用动态规划算法求解,但有时贪心算法会更简单有效。如下图所示例题,贪心所得的局部最优就是全局最优。
    贪心算法解题简单、有效,利用了问题本身的特性。但它有时并不能从局部的最优得到整体的最优。如下图所示例题,贪心所得的局部最优并非全局最优。

ps:贪心算法并不是通用方法 只是个思想