LeetCode 55 Jump Game

55. Jump Game.

Given an array of non-negative integers, you are initially positioned at the first index of the array.

Each element in the array represents your maximum jump length at that position.

Determine if you are able to reach the last index.

For example:

A = [2,3,1,1,4], return true.

A = [3,2,1,0,4], return false.


题意:给定一个数组,表示n个点,每个数组元素表示在该点能够跳跃的最大距离,判断从第一个点出发是否能够到达数组的最后一个点。


分析:从原点出发,根据数组的元素,判断是否能够到达最后一个点,这显然是一个贪心问题,特别需要注意的是:数组中的每个元素表示的能够跳跃的最大距离,在贪心算法过程中,每次跳跃不一定都需要跳跃最大距离,根据后续数组元素选择跳跃距离。(踩坑:第一次实现时根据每次都跳跃最大距离来判断,掉进坑了)


这个问题也是个类似动态规划的问题,在实现过程中,采用了一个标记数组jumped[i],初始化为false,并且用jumped[0]=true表示从第一个点出发,根据数组中元素nums[i],将能够跳跃到的地方标记为true,从前向后遍历数组中已经可以到达的元素,当能够到达的地方超过了最后一个点时,返回true,否则,遍历完整个数组后,返回false;


具体代码实现如下:

class Solution {
public:
	bool canJump(vector<int>& nums) {
		bool* jumped = new bool[nums.size() + 1];
		for (int i = 0; i < nums.size(); i++) {
			jumped[i] = false;
		}

		jumped[0] = true;
		for (int i = 0; i < nums.size(); i++) {
			if (jumped[i]) {
				if (i + nums[i] >= nums.size() - 1)
					return true;
				else { // 每次不一定要跳最大距离
					for (int j = i + 1; j <= i + nums[i]; j++)
						jumped[j] = true;
				}
			}
		}
		return false;
	}
};


分析:很明显,这种方法虽然能够被Accepted,但是这个算法的时间复杂度比O(n)要略差一些,因为在第一层循环内还有一个标记能够到达位置的循环,严格来说,这种算法也不太可取。



既然每次跳跃都一个最大距离,那么意味着每次跳跃都可以到达最大距离之前的所有位置,就可以把每个位置的标记数组简化为最远位置的标记,标记为canArrive,用于记录能够到达的最远位置。遍历数组时,也即是遍历能够到达的位置时,不断更新canArrive的位置,而在判断的时候,只需要判断canArrive是否达到了最后一个点,就可完成整个算法。


这个优化算法具体代码实现:

class Solution {
public:
	bool canJump(vector<int>& nums) {
		int canArrive = 0;
		for (int i = 0; i <= canArrive && canArrive <= nums.size() - 1; i++) {
			if (i + nums[i] > canArrive)
				canArrive = i + nums[i];
		}
		return canArrive >= nums.size() - 1;
	}
};


分析:易知,优化过的算法时间复杂度即为O(n),结果也证明这算法完成所需要的时间比之前的算法快了不止百倍。





  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值