LeetCode 198.打家劫舍
动态规划
面对一间房屋,选择
- 偷 -> 下一间房屋不能偷
- 不偷 -> 下一间房屋可以偷
确定dp数组
dp[j][i] : i间房屋可以偷窃到的最高金额
j的定义:
j = 0 : 不偷
j = 1 : 偷
dp函数:
dp[0][i] = max(dp[1][i-1],dp[0][i-1])
dp[1][i] = dp[0][i-1] + nums[i]
初始化dp数组:
dp[0][0] = 0
dp[0][1] = nums[1]
下标 | 0 | 1 | 2 | 3 |
---|---|---|---|---|
第i天的金钱 | 1 | 2 | 3 | 1 |
0 | 0 | 1 | 2 | 4 |
1 | 1 | 2 | 4 | 3 |
完整代码:
class Solution {
public:
int rob(vector<int>& nums) {
vector<vector<int>> dp(2 , vector<int>(nums.size(),0));
dp[1][0] = nums[0];
for(int i=1 ; i<nums.size() ; i++)
{
dp[0][i] = max(dp[1][i-1] , dp[0][i-1]);
dp[1][i] = dp[0][i-1] + nums[i];
}
return max(dp[0][nums.size()-1] , dp[1][nums.size()-1]);
}
};
如果是一维dp
dp[i] = dp[i-1]
dp[i] = dp[i-2] + nums[i]
所以:
dp[i] = max(dp[i-1] , dp[i-2] + nums[i])
完整代码:
class Solution {
public:
int rob(vector<int>& nums) {
if (nums.size() == 0) return 0;
if (nums.size() == 1) return nums[0];
vector<int> dp(nums.size());
dp[0] = nums[0];
dp[1] = max(nums[0], nums[1]);
for (int i = 2; i < nums.size(); i++) {
dp[i] = max(dp[i - 2] + nums[i], dp[i - 1]);
}
return dp[nums.size() - 1];
}
};