力扣第五十五题-跳跃游戏

402 阅读2分钟

这是我参与8月更文挑战的第22天,活动详情查看:8月更文挑战

前言

力扣第五十五题 跳跃游戏 如下所示:

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

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

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

示例 1:

输入: nums = [2,3,1,1,4]
输出: true
解释: 可以先跳 1 步,从下标 0 到达下标 1, 然后再从下标 1 跳 3 步到达最后一个下标。

示例 2:

输入: nums = [3,2,1,0,4]
输出: false
解释: 无论怎样,总会到达下标为 3 的位置。但该下标的最大跳跃长度是 0 , 所以永远不可能到达最后一个下标。

一、思路

这一题和 力扣第四十五题-跳跃游戏 II 是相似的,我本来也准备使用 贪心算法(已走的距离+将走的距离最大化),如果在最优的策略下都没办法到达最后一个下标,说明就无法到达。

但是后来经我聪明的女盆友提醒后发现,这一题只需要判断是否能到达数组尾部,并不需要选择最少的跳跃次数,所以根本不需要使用贪心算法(有效的减少了算法的复杂度,太牛了!)

因为最终的目的是要到达数组的尾部,所以我们可以:从数组尾部向前遍历,如果某个下标能到达尾部,则将当前下标更新为新的尾部下标。如果最后尾部下标为数组第一个下标,则返回 True

举个例子

nums = [3, 2, 2, 0, 4] 为例,初始情况尾部下标为 4

如果 nums[i] >= lastJump - i 则表示当前下标可以到达尾部下标

image.png

  1. i=3 时,不满足 nums[3] >= 4 - 3(0 < 1),故无法到达尾部下标
  2. i=2 时,满足 nums[2] >= 4 - 2(2 == 2),可以到达尾部下标,更新尾部下标为 2

image.png

  1. i=1 时,满足 nums[1] >= 2 - 1(2 > 1),可以到达尾部下标,更新尾部下标为 1

image.png

  1. i=0 时,满足 nums[0] >= 1 - 0(3 > 1),可以到达尾部下标,更新尾部下标为 0

image.png

  1. 此时尾部下标与头部下标重合,则代表该数组可以到达最后一个下标

二、实现

实现代码

实现代码与思路保持一致

    public boolean canJump(int[] nums) {
        int len = nums.length;
        int lastJump = len-1;   // 最后一个下标
        for (int i=len-2; i>-1; i--) {
            // 如果能到达最后一个元素,则更新下标
            if (nums[i] >= lastJump - i) {
                lastJump = i;
            }
        }
        return lastJump == 0;
    }

测试代码

    public static void main(String[] args) {
        int[] nums = {2,3,1,1,4};
        int[] nums1 = {3,2,1,0,4};
        boolean flag = new Number55().canJump(nums);
        System.out.println(flag);
    }

结果

image.png

三、总结

感谢看到最后,非常荣幸能够帮助到你~♥