对于第 k~(k>2)k (k>2) 间房屋,有两个选项:
偷窃第 kk 间房屋,那么就不能偷窃第 k-1k−1 间房屋,偷窃总金额为前 k-2k−2 间房屋的最高总金额与第 kk 间房屋的金额之和。
不偷窃第 kk 间房屋,偷窃总金额为前 k-1k−1 间房屋的最高总金额。
在两个选项中选择偷窃总金额较大的选项,该选项对应的偷窃总金额即为前 kk 间房屋能偷窃到的最高总金额。
用 dp[i]dp[i] 表示前 ii 间房屋能偷窃到的最高总金额,那么就有如下的状态转移方程:
\textit{dp}[i] = \max(\textit{dp}[i-2]+\textit{nums}[i], \textit{dp}[i-1]) dp[i]=max(dp[i−2]+nums[i],dp[i−1])
边界条件为:
\begin{cases} \textit{dp}[0] = \textit{nums}[0] & 只有一间房屋,则偷窃该房屋 \ \textit{dp}[1] = \max(\textit{nums}[0], \textit{nums}[1]) & 只有两间房屋,选择其中金额较高的房屋进行偷窃 \end{cases} { dp[0]=nums[0] dp[1]=max(nums[0],nums[1])
只有一间房屋,则偷窃该房屋 只有两间房屋,选择其中金额较高的房屋进行偷窃
最终的答案即为 \textit{dp}[n-1]dp[n−1],其中 nn 是数组的长度。
作者:LeetCode-Solution 链接:https://leetcode-cn.com/problems/house-robber/solution/da-jia-jie-she-by-leetcode-solution/ 来源:力扣(LeetCode) 著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
public int rob(int[] nums) { if (nums.length == 0) return 0; int n = nums.length; if (n == 1) return nums[0]; int[] dp = new int[n]; dp[0] = nums[0]; dp[1] = Math.max(nums[0], nums[1]); for (int i = 2; i < n; i++) { dp[i] = Math.max(dp[i-2] + nums[i], dp[i-1]); } return dp[n-1]; } public int rob(int[] nums) { if (nums == null || nums.length == 0) return 0; int curMax = 0, preMax = 0; for (int i = 0; i < nums.length; i++ ){ int t = curMax; curMax = Math.max(preMax + nums[i], curMax); preMax = t; } return curMax; }