{"id":809,"date":"2025-07-30T16:42:57","date_gmt":"2025-07-30T11:12:57","guid":{"rendered":"https:\/\/codeanddebug.in\/blog\/?p=809"},"modified":"2025-07-30T16:42:59","modified_gmt":"2025-07-30T11:12:59","slug":"house-robber-ii","status":"publish","type":"post","link":"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/","title":{"rendered":"House Robber II | Leetcode 213 | All 4 Solutions"},"content":{"rendered":"\n<p>You are a professional robber planning to rob houses along a street. Each house has a certain amount of money stashed. All houses at this place are&nbsp;<strong>arranged in a circle.<\/strong>&nbsp;That means the first house is the neighbor of the last one. Meanwhile, adjacent houses have a security system connected, and&nbsp;<strong>it will automatically contact the police if two adjacent houses were broken into on the same night<\/strong>.<\/p>\n\n\n\n<p>Here&#8217;s the [<strong><a href=\"https:\/\/leetcode.com\/problems\/house-robber-ii\/description\/\" target=\"_blank\" rel=\"noreferrer noopener\"><mark style=\"background-color:rgba(0, 0, 0, 0)\" class=\"has-inline-color has-vivid-purple-color\"><span style=\"text-decoration: underline;\">Problem Link<\/span><\/mark><\/a><\/strong>] to begin with.<\/p>\n\n\n\n<p>Given an integer array&nbsp;<code>nums<\/code>&nbsp;representing the amount of money of each house, return&nbsp;<em>the maximum amount of money you can rob tonight&nbsp;<strong>without alerting the police<\/strong><\/em>.<\/p>\n\n\n\n<p><strong>Example 1:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-preformatted\"><strong>Input:<\/strong> nums = [2,3,2]<br><strong>Output:<\/strong> 3<br><strong>Explanation:<\/strong> You cannot rob house 1 (money = 2) and then rob house 3 (money = 2), because they are adjacent houses.<\/pre>\n\n\n\n<p><strong>Example 2:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-preformatted\"><strong>Input:<\/strong> nums = [1,2,3,1]<br><strong>Output:<\/strong> 4<br><strong>Explanation:<\/strong> Rob house 1 (money = 1) and then rob house 3 (money = 3).<br>Total amount you can rob = 1 + 3 = 4.<\/pre>\n\n\n\n<p><strong>Example 3:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-preformatted\"><strong>Input:<\/strong> nums = [1,2,3]<br><strong>Output:<\/strong> 3<\/pre>\n\n\n\n<p><strong>Constraints:<\/strong><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><code>1 &lt;= nums.length &lt;= 100<\/code><\/li>\n\n\n\n<li><code>0 &lt;= nums[i] &lt;= 1000<\/code><\/li>\n<\/ul>\n\n\n<div style=\"max-width: -moz-fit-content; \" class=\"wp-block-ub-table-of-contents-block ub_table-of-contents ub_table-of-contents-collapsed\" id=\"ub_table-of-contents-c678782e-45b7-41c6-a27d-61e3951bbfd2\" data-linktodivider=\"false\" data-showtext=\"show\" data-hidetext=\"hide\" data-scrolltype=\"auto\" data-enablesmoothscroll=\"true\" data-initiallyhideonmobile=\"true\" data-initiallyshow=\"false\"><div class=\"ub_table-of-contents-header-container\" style=\"\">\n\t\t\t<div class=\"ub_table-of-contents-header\" style=\"text-align: left; \">\n\t\t\t\t<div class=\"ub_table-of-contents-title\">Contents:<\/div>\n\t\t\t\t<div class=\"ub_table-of-contents-header-toggle\">\n\t\t\t<div class=\"ub_table-of-contents-toggle\" style=\"\">\n\t\t\t\u00a0[<a class=\"ub_table-of-contents-toggle-link\" href=\"#\" style=\"\">show<\/a>]\n\t\t\t<\/div>\n\t\t<\/div>\n\t\t\t<\/div>\n\t\t<\/div><div class=\"ub_table-of-contents-extra-container\" style=\"\">\n\t\t\t<div class=\"ub_table-of-contents-container ub_table-of-contents-1-column ub-hide\">\n\t\t\t\t<ul style=\"\"><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#0-how-does-the-%E2%80%9Ccircular%E2%80%9D-constraint-change-things\" style=\"\">How Does the \u201cCircular\u201d Constraint Change Things?<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#1-solution-1-brute-force-recursion\" style=\"\">Solution 1: Brute Force (Recursion)<\/a><ul><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#2-intuition\" style=\"\">Intuition<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#3-detailed-approach\" style=\"\">Detailed Approach<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#4-code\" style=\"\">Code<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#5-code-explanation\" style=\"\">Code Explanation<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#6-time-and-space-complexity\" style=\"\">Time and Space Complexity<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#7-simplifying-it\" style=\"\">Simplifying It<\/a><\/li><\/ul><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#8-solution-2-memoization-top-down-dp\" style=\"\">Solution 2: Memoization (Top-Down DP)<\/a><ul><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#9-intuition\" style=\"\">Intuition<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#10-detailed-approach\" style=\"\">Detailed Approach<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#11-code\" style=\"\">Code<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#12-code-explanation\" style=\"\">Code Explanation<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#13-time-and-space-complexity\" style=\"\">Time and Space Complexity<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#14-simplifying-it\" style=\"\">Simplifying It<\/a><\/li><\/ul><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#15-solution-3-tabulation-bottom-up-dp\" style=\"\">Solution 3: Tabulation (Bottom-Up DP)<\/a><ul><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#16-intuition\" style=\"\">Intuition<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#17-detailed-approach\" style=\"\">Detailed Approach<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#18-code\" style=\"\">Code<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#19-code-explanation\" style=\"\">Code Explanation<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#20-time-and-space-complexity\" style=\"\">Time and Space Complexity<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#21-simplifying-it\" style=\"\">Simplifying It<\/a><\/li><\/ul><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#22-solution-4-space-optimized-tabulation-best-practice\" style=\"\">Solution 4: Space-Optimized Tabulation (Best Practice)<\/a><ul><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#23-intuition\" style=\"\">Intuition<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#24-detailed-approach\" style=\"\">Detailed Approach<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#25-code\" style=\"\">Code<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#26-code-explanation\" style=\"\">Code Explanation<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#27-time-and-space-complexity\" style=\"\">Time and Space Complexity<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#28-simplifying-it\" style=\"\">Simplifying It<\/a><\/li><\/ul><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#29-summary-table\" style=\"\">Summary Table<\/a><\/li><li style=\"\"><a href=\"https:\/\/codeanddebug.in\/blog\/house-robber-ii\/#30-conclusion\" style=\"\">Conclusion<\/a><\/li><\/ul>\n\t\t\t<\/div>\n\t\t<\/div><\/div>\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"0-how-does-the-%E2%80%9Ccircular%E2%80%9D-constraint-change-things\">How Does the \u201cCircular\u201d Constraint Change Things?<\/h2>\n\n\n\n<p>In the original House Robber, you could simply decide &#8220;rob or skip&#8221; for each house, moving linearly. Now, if you rob the first house, you can&#8217;t rob the last, and vice versa.<br>So, split into two scenarios:<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>Rob houses 0 to n-2 (skip the last house).<\/li>\n\n\n\n<li>Rob houses 1 to n-1 (skip the first house).<\/li>\n<\/ol>\n\n\n\n<p>Take the maximum of the two.<br>Let\u2019s apply different DP approaches for each scenario.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"1-solution-1-brute-force-recursion\">Solution 1: Brute Force (Recursion)<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"2-intuition\">Intuition<\/h3>\n\n\n\n<p>At every step, you have two choices:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Pick the current house (and thus skip the previous one)<\/li>\n\n\n\n<li>Skip the current house (and take the best from earlier)<\/li>\n<\/ul>\n\n\n\n<p>Because of the circular nature, we run the logic twice:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Once excluding the last house (<code>nums[0 : n-1]<\/code>)<\/li>\n\n\n\n<li>Once excluding the first house (<code>nums[1 : n]<\/code>)<\/li>\n<\/ul>\n\n\n\n<p>Take the max of both results.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"3-detailed-approach\">Detailed Approach<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Base Cases:<\/strong>\n<ul class=\"wp-block-list\">\n<li>If index == 0: Only one house, so rob it.<\/li>\n\n\n\n<li>If index == -1: No houses left, so rob nothing.<\/li>\n<\/ul>\n<\/li>\n\n\n\n<li><strong>Recursive Cases:<\/strong>\n<ul class=\"wp-block-list\">\n<li><code>pick = nums[index] + solve(index-2, nums)<\/code><\/li>\n\n\n\n<li><code>notpick = solve(index-1, nums)<\/code><\/li>\n\n\n\n<li>Return\u00a0<code>max(pick, notpick)<\/code><\/li>\n<\/ul>\n<\/li>\n\n\n\n<li><strong>Do this for both possible slices.<\/strong><\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"4-code\">Code<\/h3>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro cbp-has-line-numbers\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;--cbp-line-number-color:#D4D4D4;--cbp-line-number-width:calc(2 * 0.6 * .875rem);line-height:1.5rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:block;padding:16px 0 0 16px;margin-bottom:-1px;width:100%;text-align:left;background-color:#1E1E1E\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"54\" height=\"14\" viewBox=\"0 0 54 14\"><g fill=\"none\" fill-rule=\"evenodd\" transform=\"translate(1 1)\"><circle cx=\"6\" cy=\"6\" r=\"6\" fill=\"#FF5F56\" stroke=\"#E0443E\" stroke-width=\".5\"><\/circle><circle cx=\"26\" cy=\"6\" r=\"6\" fill=\"#FFBD2E\" stroke=\"#DEA123\" stroke-width=\".5\"><\/circle><circle cx=\"46\" cy=\"6\" r=\"6\" fill=\"#27C93F\" stroke=\"#1AAB29\" stroke-width=\".5\"><\/circle><\/g><\/svg><\/span><span role=\"button\" tabindex=\"0\" data-code=\"class Solution:\n    def solve(self, index, nums):\n        # If only one house left, rob it\n        if index == 0:\n            return nums[index]\n        # If no houses left, rob nothing\n        if index == -1:\n            return 0\n        # Option 1: Pick current house and move two steps back\n        pick = nums[index] + self.solve(index - 2, nums)\n        # Option 2: Skip current house and move one step back\n        notpick = self.solve(index - 1, nums)\n        # Return max loot possible at this index\n        return max(pick, notpick)\n    \n    def rob(self, nums: List[int]) -&gt; int:\n        # Base case: only one house (no circle constraint)\n        if len(nums) == 1:\n            return nums[0]\n        n = len(nums)\n        # Scenario 1: Rob from 0 to n-2\n        ans1 = self.solve(n - 2, nums[0 : n - 1])\n        # Scenario 2: Rob from 1 to n-1\n        ans2 = self.solve(n - 2, nums[1 : n])\n        # Return the best out of both possibilities\n        return max(ans1, ans2)\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #569CD6\">class<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #4EC9B0\">Solution<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">solve<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">index<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># If only one house left, rob it<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index == <\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># If no houses left, rob nothing<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index == -<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #B5CEA8\">0<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Option 1: Pick current house and move two steps back<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        pick = nums[index] + <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(index - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Option 2: Skip current house and move one step back<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        notpick = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(index - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">, nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Return max loot possible at this index<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(pick, notpick)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">rob<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">: List[<\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">]) -&gt; <\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Base case: only one house (no circle constraint)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums) == <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Scenario 1: Rob from 0 to n-2<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans1 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(n - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\"> : n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Scenario 2: Rob from 1 to n-1<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans2 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(n - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums[<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\"> : n])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Return the best out of both possibilities<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(ans1, ans2)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"5-code-explanation\">Code Explanation<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><code>solve(index, nums)<\/code>\u00a0recursively computes the best you can do for a slice.<\/li>\n\n\n\n<li>Careful splitting ensures the\u00a0<strong>circle<\/strong>\u00a0is not broken (never include both first and last house).<\/li>\n\n\n\n<li>Calls\u00a0<code>solve<\/code>\u00a0for both scenarios, returns the maximum possible loot.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"6-time-and-space-complexity\">Time and Space Complexity<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Time:<\/strong>\u00a0O(2^n) &#8211; Each call can branch into two subproblems; exponential.<\/li>\n\n\n\n<li><strong>Space:<\/strong>\u00a0O(n) &#8211; Due to recursion stack.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"7-simplifying-it\">Simplifying It<\/h3>\n\n\n\n<p>Think: You\u2019re trying every possible rob\/skip path for both possible ranges, but you forget the results of previous calculations. Practical only for small n.<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"8-solution-2-memoization-top-down-dp\">Solution 2: Memoization (Top-Down DP)<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"9-intuition\">Intuition<\/h3>\n\n\n\n<p>In brute force, the same subproblems are recalculated many times. Memoization adds a DP array to remember results for each index and subarray. Same two scenarios apply (exclude first, exclude last); now we save time by caching.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"10-detailed-approach\">Detailed Approach<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>DP array<\/strong>\u00a0of length n-1 (as we slice nums to length n-1 each time).<\/li>\n\n\n\n<li>For each call, if value already computed (<code>dp[index] != -1<\/code>), return cached result.<\/li>\n\n\n\n<li>Otherwise, compute as with recursion and store result in dp array.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"11-code\">Code<\/h3>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro cbp-has-line-numbers\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;--cbp-line-number-color:#D4D4D4;--cbp-line-number-width:calc(2 * 0.6 * .875rem);line-height:1.5rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:block;padding:16px 0 0 16px;margin-bottom:-1px;width:100%;text-align:left;background-color:#1E1E1E\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"54\" height=\"14\" viewBox=\"0 0 54 14\"><g fill=\"none\" fill-rule=\"evenodd\" transform=\"translate(1 1)\"><circle cx=\"6\" cy=\"6\" r=\"6\" fill=\"#FF5F56\" stroke=\"#E0443E\" stroke-width=\".5\"><\/circle><circle cx=\"26\" cy=\"6\" r=\"6\" fill=\"#FFBD2E\" stroke=\"#DEA123\" stroke-width=\".5\"><\/circle><circle cx=\"46\" cy=\"6\" r=\"6\" fill=\"#27C93F\" stroke=\"#1AAB29\" stroke-width=\".5\"><\/circle><\/g><\/svg><\/span><span role=\"button\" tabindex=\"0\" data-code=\"class Solution:\n    def solve(self, index, nums, dp):\n        # If only one house left, rob it\n        if index == 0:\n            return nums[index]\n        # If no houses left\n        if index == -1:\n            return 0\n        # Use cached value if available\n        if dp[index] != -1:\n            return dp[index]\n        # Option 1: Pick and add result from index-2\n        pick = nums[index] + self.solve(index - 2, nums, dp)\n        # Option 2: Skip current house\n        notpick = self.solve(index - 1, nums, dp)\n        dp[index] = max(pick, notpick)\n        return dp[index]\n    \n    def rob(self, nums: List[int]) -&gt; int:\n        if len(nums) == 1:\n            return nums[0]\n        n = len(nums)\n        # Rob from 0 to n-2\n        dp1 = [-1] * (n - 1)\n        ans1 = self.solve(n - 2, nums[0 : n - 1], dp1)\n        # Rob from 1 to n-1\n        dp2 = [-1] * (n - 1)\n        ans2 = self.solve(n - 2, nums[1 : n], dp2)\n        return max(ans1, ans2)\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #569CD6\">class<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #4EC9B0\">Solution<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">solve<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">index<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">dp<\/span><span style=\"color: #D4D4D4\">):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># If only one house left, rob it<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index == <\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># If no houses left<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index == -<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #B5CEA8\">0<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Use cached value if available<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> dp[index] != -<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> dp[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Option 1: Pick and add result from index-2<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        pick = nums[index] + <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(index - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums, dp)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Option 2: Skip current house<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        notpick = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(index - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">, nums, dp)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        dp[index] = <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(pick, notpick)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> dp[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">rob<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">: List[<\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">]) -&gt; <\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums) == <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Rob from 0 to n-2<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        dp1 = [-<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">] * (n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans1 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(n - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\"> : n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">], dp1)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Rob from 1 to n-1<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        dp2 = [-<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">] * (n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans2 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(n - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">, nums[<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\"> : n], dp2)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(ans1, ans2)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"12-code-explanation\">Code Explanation<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Like pure recursion, but now each subproblem is solved just once, thanks to the dp array.<\/li>\n\n\n\n<li>Both slices (<code>nums[0:n-1]<\/code>\u00a0and\u00a0<code>nums[1:n]<\/code>) use separate dp arrays, ensuring circle constraint is always satisfied.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"13-time-and-space-complexity\">Time and Space Complexity<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Time:<\/strong>\u00a0O(n) per subarray (n-1), so O(n) total.<\/li>\n\n\n\n<li><strong>Space:<\/strong>\u00a0O(n) for DP arrays + O(n) for stack frames.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"14-simplifying-it\">Simplifying It<\/h3>\n\n\n\n<p>Now you keep a notebook for each scenario and never recalculate any decision. Much faster, good for large n!<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"15-solution-3-tabulation-bottom-up-dp\">Solution 3: Tabulation (Bottom-Up DP)<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"16-intuition\">Intuition<\/h3>\n\n\n\n<p>Instead of starting from end and recursing, fill up DP array from base to target using a for-loop. For each index, loot = max(current house + dp[index-2], dp[index-1]).<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"17-detailed-approach\">Detailed Approach<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li>For each scenario (exclude last or exclude first), make separate pass.<\/li>\n\n\n\n<li>Start with\u00a0<code>dp = nums<\/code><\/li>\n\n\n\n<li>For each index,\n<ul class=\"wp-block-list\">\n<li>If index > 1:<br><code>pick = nums[index] + dp[index-2]<\/code><\/li>\n\n\n\n<li>Else:<br><code>pick = nums[index]<\/code><\/li>\n\n\n\n<li>not_pick = dp[index-1]<\/li>\n\n\n\n<li>dp[index] = max(pick, not_pick)<\/li>\n<\/ul>\n<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"18-code\">Code<\/h3>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro cbp-has-line-numbers\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;--cbp-line-number-color:#D4D4D4;--cbp-line-number-width:calc(2 * 0.6 * .875rem);line-height:1.5rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:block;padding:16px 0 0 16px;margin-bottom:-1px;width:100%;text-align:left;background-color:#1E1E1E\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"54\" height=\"14\" viewBox=\"0 0 54 14\"><g fill=\"none\" fill-rule=\"evenodd\" transform=\"translate(1 1)\"><circle cx=\"6\" cy=\"6\" r=\"6\" fill=\"#FF5F56\" stroke=\"#E0443E\" stroke-width=\".5\"><\/circle><circle cx=\"26\" cy=\"6\" r=\"6\" fill=\"#FFBD2E\" stroke=\"#DEA123\" stroke-width=\".5\"><\/circle><circle cx=\"46\" cy=\"6\" r=\"6\" fill=\"#27C93F\" stroke=\"#1AAB29\" stroke-width=\".5\"><\/circle><\/g><\/svg><\/span><span role=\"button\" tabindex=\"0\" data-code=\"class Solution:\n    def solve(self, nums):\n        n = len(nums)\n        dp = [-1] * n\n        dp[0] = nums[0]\n        for index in range(1, n):\n            # Pick current + two steps back if possible\n            if index &gt; 1:\n                pick = nums[index] + dp[index - 2]\n            else:\n                pick = nums[index]\n            # Skip current, take previous result\n            not_pick = dp[index - 1]\n            dp[index] = max(pick, not_pick)\n        return dp[n - 1]\n    \n    def rob(self, nums: List[int]) -&gt; int:\n        n = len(nums)\n        if n == 1:\n            return nums[0]\n        # Exclude last and exclude first scenarios\n        ans1 = self.solve(nums[0 : n - 1])\n        ans2 = self.solve(nums[1 : n])\n        return max(ans1, ans2)\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #569CD6\">class<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #4EC9B0\">Solution<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">solve<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        dp = [-<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">] * n<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        dp[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">] = nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">for<\/span><span style=\"color: #D4D4D4\"> index <\/span><span style=\"color: #C586C0\">in<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">range<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">, n):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #6A9955\"># Pick current + two steps back if possible<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index &gt; <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">                pick = nums[index] + dp[index - <\/span><span style=\"color: #B5CEA8\">2<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">else<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">                pick = nums[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #6A9955\"># Skip current, take previous result<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            not_pick = dp[index - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            dp[index] = <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(pick, not_pick)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> dp[n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">rob<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">: List[<\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">]) -&gt; <\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> n == <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Exclude last and exclude first scenarios<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans1 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\"> : n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans2 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(nums[<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\"> : n])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(ans1, ans2)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"19-code-explanation\">Code Explanation<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li>The\u00a0<code>solve<\/code>\u00a0function fills dp array from left to right, building up possibilities step by step.<\/li>\n\n\n\n<li>Main rob function checks for the single house case; otherwise, runs both possible cases.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"20-time-and-space-complexity\">Time and Space Complexity<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Time:<\/strong>\u00a0O(n) per scenario, so O(n) total.<\/li>\n\n\n\n<li><strong>Space:<\/strong>\u00a0O(n) for dp array.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"21-simplifying-it\">Simplifying It<\/h3>\n\n\n\n<p>You write a plan for each possible chain of houses, filling the results for each step, and never look back!<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"22-solution-4-space-optimized-tabulation-best-practice\">Solution 4: Space-Optimized Tabulation (Best Practice)<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"23-intuition\">Intuition<\/h3>\n\n\n\n<p>While building the dp array, we only ever need the last two values. Replace array with two variables (<code>prev<\/code>,&nbsp;<code>prev2<\/code>) for memory efficiency; great for interviews!<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"24-detailed-approach\">Detailed Approach<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li>For each slice, initialize:\n<ul class=\"wp-block-list\">\n<li><code>prev<\/code>\u00a0as the value at index 0 (nums)<\/li>\n\n\n\n<li><code>prev2<\/code>\u00a0to 0<\/li>\n<\/ul>\n<\/li>\n\n\n\n<li>For each house, update:\n<ul class=\"wp-block-list\">\n<li>If index > 1:\n<ul class=\"wp-block-list\">\n<li>pick = nums[index] + prev2<\/li>\n<\/ul>\n<\/li>\n\n\n\n<li>Else:\n<ul class=\"wp-block-list\">\n<li>pick = nums[index]<\/li>\n<\/ul>\n<\/li>\n\n\n\n<li>not_pick = prev<\/li>\n\n\n\n<li>curr = max(pick, not_pick)<\/li>\n\n\n\n<li>Slide window: prev2 = prev; prev = curr<\/li>\n<\/ul>\n<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"25-code\">Code<\/h3>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro cbp-has-line-numbers\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;--cbp-line-number-color:#D4D4D4;--cbp-line-number-width:calc(2 * 0.6 * .875rem);line-height:1.5rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:block;padding:16px 0 0 16px;margin-bottom:-1px;width:100%;text-align:left;background-color:#1E1E1E\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"54\" height=\"14\" viewBox=\"0 0 54 14\"><g fill=\"none\" fill-rule=\"evenodd\" transform=\"translate(1 1)\"><circle cx=\"6\" cy=\"6\" r=\"6\" fill=\"#FF5F56\" stroke=\"#E0443E\" stroke-width=\".5\"><\/circle><circle cx=\"26\" cy=\"6\" r=\"6\" fill=\"#FFBD2E\" stroke=\"#DEA123\" stroke-width=\".5\"><\/circle><circle cx=\"46\" cy=\"6\" r=\"6\" fill=\"#27C93F\" stroke=\"#1AAB29\" stroke-width=\".5\"><\/circle><\/g><\/svg><\/span><span role=\"button\" tabindex=\"0\" data-code=\"class Solution:\n    def solve(self, nums):\n        n = len(nums)\n        prev = nums[0]   # DP for index - 1\n        prev2 = 0        # DP for index - 2\n        for index in range(1, n):\n            # Pick current house and add loot from two steps back\n            if index &gt; 1:\n                pick = nums[index] + prev2\n            else:\n                pick = nums[index]\n            # Skip current house, use prev result\n            not_pick = prev\n            curr = max(pick, not_pick)\n            # Update window\n            prev2 = prev\n            prev = curr\n        return prev\n    \n    def rob(self, nums: List[int]) -&gt; int:\n        n = len(nums)\n        if n == 1:\n            return nums[0]\n        # Try both scenarios (excluding first or last house)\n        ans1 = self.solve(nums[0 : n - 1])\n        ans2 = self.solve(nums[1 : n])\n        return max(ans1, ans2)\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #569CD6\">class<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #4EC9B0\">Solution<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">solve<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        prev = nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]   <\/span><span style=\"color: #6A9955\"># DP for index - 1<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        prev2 = <\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># DP for index - 2<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">for<\/span><span style=\"color: #D4D4D4\"> index <\/span><span style=\"color: #C586C0\">in<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">range<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">, n):<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #6A9955\"># Pick current house and add loot from two steps back<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> index &gt; <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">                pick = nums[index] + prev2<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">else<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">                pick = nums[index]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #6A9955\"># Skip current house, use prev result<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            not_pick = prev<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            curr = <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(pick, not_pick)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #6A9955\"># Update window<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            prev2 = prev<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            prev = curr<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> prev<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    <\/span><span style=\"color: #569CD6\">def<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">rob<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #9CDCFE\">self<\/span><span style=\"color: #D4D4D4\">, <\/span><span style=\"color: #9CDCFE\">nums<\/span><span style=\"color: #D4D4D4\">: List[<\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">]) -&gt; <\/span><span style=\"color: #4EC9B0\">int<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        n = <\/span><span style=\"color: #DCDCAA\">len<\/span><span style=\"color: #D4D4D4\">(nums)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">if<\/span><span style=\"color: #D4D4D4\"> n == <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">:<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">            <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\">]<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #6A9955\"># Try both scenarios (excluding first or last house)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans1 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(nums[<\/span><span style=\"color: #B5CEA8\">0<\/span><span style=\"color: #D4D4D4\"> : n - <\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\">])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        ans2 = <\/span><span style=\"color: #569CD6\">self<\/span><span style=\"color: #D4D4D4\">.solve(nums[<\/span><span style=\"color: #B5CEA8\">1<\/span><span style=\"color: #D4D4D4\"> : n])<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        <\/span><span style=\"color: #C586C0\">return<\/span><span style=\"color: #D4D4D4\"> <\/span><span style=\"color: #DCDCAA\">max<\/span><span style=\"color: #D4D4D4\">(ans1, ans2)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"26-code-explanation\">Code Explanation<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Only two variables needed throughout; for each scenario, make a linear scan.<\/li>\n\n\n\n<li>Final answer is the better loot from both scenarios, so the\u00a0<strong>circle<\/strong>\u00a0is always respected.<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"27-time-and-space-complexity\">Time and Space Complexity<\/h3>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Time:<\/strong>\u00a0O(n)<\/li>\n\n\n\n<li><strong>Space:<\/strong>\u00a0O(1) (just variables, not arrays)<\/li>\n<\/ul>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"28-simplifying-it\">Simplifying It<\/h3>\n\n\n\n<p>It\u2019s like moving through the houses with a calculator, only tracking the last two amounts, always keeping memory and speed at max efficiency!<\/p>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"29-summary-table\">Summary Table<\/h2>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Approach<\/th><th>Time<\/th><th>Space<\/th><th>Difficulty<\/th><th>Use Case<\/th><\/tr><\/thead><tbody><tr><td>Recursion (Brute Force)<\/td><td>O(2^n)<\/td><td>O(n)<\/td><td>Easy<\/td><td>Understanding choices<\/td><\/tr><tr><td>Memoization (Top-Down DP)<\/td><td>O(n)<\/td><td>O(n)<\/td><td>Medium<\/td><td>Learning DP, larger n<\/td><\/tr><tr><td>Tabulation (Bottom-Up DP)<\/td><td>O(n)<\/td><td>O(n)<\/td><td>Medium<\/td><td>Iteration-based DP<\/td><\/tr><tr><td>Space-Optimized Tabulation<\/td><td>O(n)<\/td><td>O(1)<\/td><td>Medium-Hard<\/td><td>Best for interviews\/coding<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"30-conclusion\">Conclusion<\/h2>\n\n\n\n<p>The&nbsp;<strong>House Robber II<\/strong>&nbsp;problem is a powerful demonstration of how a small twist (the circular street) can change a familiar dynamic programming pattern. Start with recursion for clarity, move through memoization and tabulation, and finish with sleek space optimization for interviews or production code. Practice with variants like &#8220;House Robber I&#8221; and related DP problems to reinforce your foundations.<\/p>\n\n\n\n<div class=\"wp-block-buttons is-content-justification-center is-layout-flex wp-container-core-buttons-is-layout-16018d1d wp-block-buttons-is-layout-flex\">\n<div class=\"wp-block-button\"><a class=\"wp-block-button__link wp-element-button\" href=\"https:\/\/codeanddebug.in\/course\/zero-to-hero-python-dsa\" target=\"_blank\" rel=\"noreferrer noopener\">Join our Advance DSA COURSE<\/a><\/div>\n<\/div>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<p><em>For any changes to the article, kindly email at <a href=\"mailto:code@codeanddebug.in\" target=\"_blank\" rel=\"noreferrer noopener\">code@codeanddebug.in<\/a> or contact us at <a href=\"tel:+91-9712928220\" target=\"_blank\" rel=\"noreferrer noopener\">+91-9712928220<\/a>.<\/em><\/p>\n","protected":false},"excerpt":{"rendered":"<p>You are a professional robber planning to rob houses along a street. Each house has a certain amount of money stashed. All houses at this place are&nbsp;arranged in a circle.&nbsp;That means the first house is the neighbor of the last one. Meanwhile, adjacent houses have a security system connected, and&nbsp;it will automatically contact the police<\/p>\n","protected":false},"author":1,"featured_media":811,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[3,5],"tags":[36,18],"class_list":{"0":"post-809","1":"post","2":"type-post","3":"status-publish","4":"format-standard","5":"has-post-thumbnail","7":"category-data-structures-and-algorithm","8":"category-expert","9":"tag-dynamic-programming","10":"tag-hard"},"featured_image_src":"https:\/\/codeanddebug.in\/blog\/wp-content\/uploads\/2025\/07\/house-robber-2-featured-image.png","author_info":{"display_name":"codeanddebug","author_link":"https:\/\/codeanddebug.in\/blog\/author\/codeanddebug\/"},"_links":{"self":[{"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/posts\/809","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/comments?post=809"}],"version-history":[{"count":2,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/posts\/809\/revisions"}],"predecessor-version":[{"id":819,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/posts\/809\/revisions\/819"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/media\/811"}],"wp:attachment":[{"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/media?parent=809"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/categories?post=809"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/codeanddebug.in\/blog\/wp-json\/wp\/v2\/tags?post=809"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}