本次题目
- 198 打家劫舍
- 213 打家劫舍II
- 337 打家劫舍III
198 打家劫舍
- DP:
- 定义dp数组dp[i]表示下标i(包括i)以内的房屋,最多偷窃金额为dp[i];
- 递推公式dp[i] = max(dp[i - 2] + nums[i], dp[i - 1]);
- 初始化dp[0] = nums[0], dp[1] = max(nums[0], nums[1]);
- 遍历顺序正序;
- 举例。
class Solution {
public int rob(int[] nums) {
if(nums.length == 1) return nums[0];
int[] dp = new int[nums.length];
dp[0] = nums[0];
dp[1] = Math.max(nums[0], nums[1]);
for(int i = 2; i < nums.length; i++){
dp[i] = Math.max(dp[i - 2] + nums[i], dp[i - 1]);
}
return dp[nums.length - 1];
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
213 打家劫舍II
- DP:同上,但是邻居首尾相接,因此首尾只能取一个,分别考虑首尾,最后取最大值。
- 注意:上下标均可达;定义dp数组统一长度为给定数组长度,最后取下标即可,初始化时从上标开始。
class Solution {
public int rob(int[] nums) {
if(nums.length == 1) return nums[0];
int head = robRange(nums, 0, nums.length - 2);
int tail = robRange(nums, 1, nums.length - 1);
return Math.max(head, tail);
}
private int robRange(int[] nums, int start, int end){
if(start == end) return nums[start];
int[] dp = new int[nums.length];
dp[start] = nums[start];
dp[start + 1] = Math.max(nums[start], nums[start + 1]);
for(int i = start + 2; i <= end; i++){
dp[i] = Math.max(dp[i - 1], dp[i - 2] + nums[i]);
}
return dp[end];
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
337 打家劫舍III
- DP:同上,但是邻居为二叉树结构,因此需要在递归过程中进行DP。
- 定义dp数组表示当前节点偷或不偷得到的金钱(长度为2,0为不偷,1为偷);如果当前节点为空,则返回[0,0];
- 遍历顺序为后序遍历,通过当前节点的左右孩子情况来做下一步计算;如果不偷当前节点,则取左右孩子的dp数组中的最大值之和;若偷当前节点,则不能偷左右孩子;举例。
class Solution {
public int rob(TreeNode root) {
int[] res = robTree(root);
return Math.max(res[0], res[1]);
}
private int[] robTree(TreeNode root){
int[] dp = new int[2];
if(root == null) return dp;
int[] left = robTree(root.left);
int[] right = robTree(root.right);
dp[0] = Math.max(left[0], left[1]) + Math.max(right[0], right[1]);
dp[1] = root.val + left[0] + right[0];
return dp;
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41