动态规划
解题思路
确定 dp 数组以及下标的含义:dp[i]:考虑下标 [0, i] 的房屋,最多可以偷窃的金额为 dp[i]
确定递推公式:dp[i] = max(dp[i - 2] + nums[i], dp[i - 1]),dp[i] 由两种情况中的最大值转移过来:
- 偷第 i 房间:第 i - 1 房一定是不考虑的,需要偷窃第 i - 2 房,即:最多可以偷窃的金额为 dp[i-2] 加上第 i 房间偷到的钱,则 dp[i] = dp[i - 2] + nums[i];
- 不偷第 i 房间:可以偷窃第 i - 1 房,则 dp[i] = dp[i - 1];
如何初始化 dp 数组:
- 递推公式的基础就是 dp[0] 和 dp[1];
- dp[0] 一定是 nums[0],dp[1] 就是 nums[0] 和 nums[1] 的最大值;
确定遍历顺序:dp[i] 是根据 dp[i - 2] 和 dp[i - 1] 推导出来的,那么一定是从前到后遍历;
举例推导 dp 数组:以 [1, 2, 3, 1] 为例:
第 0 个房间 第 1 个房间 第 2 个房间 第 3 个房间 dp[i] 1 2 4 4
复杂度
-
时间复杂度:
O(n)
,遍历一次数组; -
空间复杂度:
O(n)
;
代码实现
const rob = (nums) => {
const len = nums.length;
// 1. 声明 dp
const dp = new Array(len).fill(0);
// 2. 初始化 dp
dp[0] = nums[0];
dp[1] = Math.max(nums[0], nums[1]);
// 3. 从第三个位置开始遍历
for (let i = 2; i < len; i++) {
dp[i] = Math.max(dp[i - 2] + nums[i], dp[i - 1]);
}
// 4. 返回最后最大的项
return dp[len - 1];
};
参考资料
leetcode🧑💻 279. 完全平方数
上一篇