403. Frog Jump
https://leetcode.com/problems/frog-jump/description/
给一个数组,元素的值代表横轴的坐标,从0点起跳可跳一步远,以后只要上次跳了k-1, k 或k+1步, 那本次就可以跳k步,问能否跳到最后一个元素代表的位置。问能否跳到解法无非DP或greedy。action为从前面的任一位置j跳到当前位置i,i和j的距离为k, action成功与否受限于跳到上一位置j 是否用了k-1, k或k步。因此状态记录对于位置i, 所有可能的k。
/*
* @lc app=leetcode id=403 lang=cpp
*
* [403] Frog Jump
*
* https://leetcode.com/problems/frog-jump/description/
*
* algorithms
* Hard (36.87%)
* Likes: 601
* Dislikes: 72
* Total Accepted: 59.3K
* Total Submissions: 160.1K
* Testcase Example: '[0,1,3,4,5,7,9,10,12]'
*
* A frog is crossing a river. The river is divided into x units and at each
* unit there may or may not exist a stone. The frog can jump on a stone, but
* it must not jump into the water.
*
* Given a list of stones' positions (in units) in sorted ascending order,
* determine if the frog is able to cross the river by landing on the last
* stone. Initially, the frog is on the first stone and assume the first jump
* must be 1 unit.
*
*
* If the frog's last jump was k units, then its next jump must be either k -
* 1, k, or k + 1 units. Note that the frog can only jump in the forward
* direction.
*
* Note:
*
* The number of stones is ≥ 2 and is < 1,100.
* Each stone's position will be a non-negative integer < 2^31.
* The first stone's position is always 0.
*
*
*
* Example 1:
*
* [0,1,3,5,6,8,12,17]
*
* There are a total of 8 stones.
* The first stone at the 0th unit, second stone at the 1st unit,
* third stone at the 3rd unit, and so on...
* The last stone at the 17th unit.
*
* Return true. The frog can jump to the last stone by jumping
* 1 unit to the 2nd stone, then 2 units to the 3rd stone, then
* 2 units to the 4th stone, then 3 units to the 6th stone,
* 4 units to the 7th stone, and 5 units to the 8th stone.
*
*
*
* Example 2:
*
* [0,1,2,3,4,8,9,11]
*
* Return false. There is no way to jump to the last stone as
* the gap between the 5th and 6th stone is too large.
*
*
*/
class Solution {
public:
bool canCross(vector<int>& stones) {
const int N = stones.size();
vector<unordered_set<int>> dp(N);
dp[0].insert(0);
for (int i = 1; i < N; ++i) {
for (int j = i - 1; j >= 0; --j) {
int k = stones[i] - stones[j];
if (k >= N) break;
if (dp[j].count(k - 1) || dp[j].count(k) || dp[j].count(k + 1)) {
dp[i].insert(k);
}
if ((i == N - 1) && dp[i].count(k)) return true;
}
}
return false;
}
};
Last updated
Was this helpful?