题目:
给定一个非负整数数组,你最初位于数组的第一个位置。
数组中的每个元素代表你在该位置可以跳跃的最大长度。
判断你是否能够到达最后一个位置。
示例 1:
输入: [2,3,1,1,4] 输出: true 解释: 从位置 0 到 1 跳 1 步, 然后跳 3 步到达最后一个位置。
示例 2:
输入: [3,2,1,0,4] 输出: false 解释: 无论怎样,你总会到达索引为 3 的位置。但该位置的最大跳跃长度是 0 , 所以你永远不可能到达最后一个位置。
算法过程:遍历数组,但是每遍历到一个index我们都得思考,我们跳跃能跳跃到这个地方吗?于是我们会有一个历史能达到的最大的index,去通过大小对比来判断我们能不能到达当前的index。如果能的话,我们就需要更新当前的历史最大的index。
如果最后能让我们遍历到最后一个index,也就是成功完全遍历所有的index,我们就能成功走完这个数组
算法证明:假设当前历史允许我们跳的最大的index < 我们要跳入的这个index,说明前面的所有情况都不足以支持我们跳到当前的这个index,所以跳跃失败。
扫描二维码关注公众号,回复:
2650964 查看本文章
代码:
class Solution:
def canJump(self, nums):
"""
:type nums: List[int]
:rtype: bool
"""
maxPos = 0
result = False
for i in range(len(nums)-1):
#如果历史最高高度达不到我们目前的index
if maxPos < i:
return False
#更新历史最大值
maxPos = max(maxPos, nums[i] + i)
#判断是否完全通过
if maxPos >= len(nums) - 1:
result = True
return result
以上思路已经很好理解了,但翻大神笔记还是有一种更强的。
#最简单的思路
class Solution:
def canJump(self, nums):
"""
:type nums: List[int]
:rtype: bool
"""
#从最后一位开始
i = len(nums) - 1
for j in range(len(nums)-2, -1, -1):
#如果i位能被j位获取到
if i - j <= nums[j]:
#我们的i位就往前挪
i = j
#最后看i能不能到达第一位
return i == 0
为什么我要说这个呢,因为当我看到这个代码的时候,我想的是为什么不能从头开始遍历??非要从尾部开始??展示自己非人类的思维吗??后来等我写完代码遇到bug后,才知道人家这样写的用意。。。
总结:对于这种跳跃数组的问题,也就是要到达的位置与它的每一项关系紧密的问题,第一我们可以通过保存最大范围也就是历史最大index的方法去解决。第二,我们也可以尝试着用逆序去思考,看模拟每一步能不能走成功。