leetcode213.打家劫舍II(java):动态规划

题目
leetcode213.打家劫舍II(java):动态规划_第1张图片
思路
这个和198题相比,是多了一个限制条件,就是选了第一家就不能选最后一家。
所以假设p1是不偷最后一家时最大的偷窃金额,p2是不偷第一家是最大的偷窃金额,那最后的结果就是Math.max(p1,p2)。
p1,p2的计算就是两个198问题。

具体代码

class Solution {
     
    public int rob(int[] nums) {
     
        if(nums.length == 1){
     
            return nums[0];
        }
        int p1 = stolen(nums,0);
        int p2 = stolen(nums,nums.length-1);
        return Math.max(p1,p2);
    }
    public int stolen(int[]nums,int x){
     
    //注意:这里我原来想就是把不偷的第一家/最后一家的nums[i]置为0,但是nums是一个数组对象,是直接改变的,而不是改变副本,所以不可以这样赋值。
        int dp[] = new int[nums.length+2];
        for(int i = 0;i < nums.length;i++){
     
        //于是改成这样,坐标相等,就加0,不改变原来nums[i]的值。
            if(i == x){
     
                 dp[i+2] = Math.max(dp[i],dp[i+1]);
                 continue;
            }
            dp[i+2] = Math.max(dp[i]+nums[i],dp[i+1]);
        }
        return dp[nums.length+1];
    }
}

看了一个leetcode题解,把空间复杂度降到O(1)

class Solution {
     
    public int rob(int[] nums) {
     
        if(nums.length == 0) return 0;
        if(nums.length == 1) return nums[0];
        return Math.max(myRob(Arrays.copyOfRange(nums, 0, nums.length - 1)), 
                        myRob(Arrays.copyOfRange(nums, 1, nums.length)));
    }
    private int myRob(int[] nums) {
     
        int pre = 0, cur = 0, tmp;
        for(int num : nums) {
     
            tmp = cur;
            cur = Math.max(pre + num, cur);
            pre = tmp;
        }
        return cur;
    }
}

参考链接:https://leetcode-cn.com/problems/house-robber-ii/solution/213-da-jia-jie-she-iidong-tai-gui-hua-jie-gou-hua-/

你可能感兴趣的:(leetcode)