描述
你是一个经验丰富的小偷,准备偷沿街的一排房间,每个房间都存有一定的现金,为了防止被发现,你不能偷相邻的两家,即,如果偷了第一家,就不能再偷第二家;如果偷了第二家,那么就不能偷第一家和第三家。
给定一个整数数组nums,数组中的元素表示每个房间存有的现金数额,请你计算在不被发现的前提下最多的偷窃金额。

数据范围:数组长度满足 1≤n≤2×105 1 \le n \le 2\times 10^5\ 1≤n≤2×105 ,数组中每个值满足 1≤num[i]≤5000 1 \le num[i] \le 5000 \ 1≤num[i]≤5000
示例1

输入:[1,2,3,4]
返回值: 6
说明: 最优方案是偷第 2,4 个房间

示例2

输入: [1,3,6]
返回值:7
说明:最优方案是偷第 1,3个房间

示例3

输入: [2,10,5]
返回值: 10
说明: 最优方案是偷第 2 个房间

思路:

或许有人认为利用贪心思想,偷取最多人家的钱就可以了,要么偶数家要么奇数家全部的钱,但是有时候会为了偷取更多的钱,或许可能会连续放弃两家不偷,因此这种方案行不通,我们依旧考虑动态规划。

具体做法:

step 1:用dp[i]表示长度为i的数组,最多能偷取到多少钱,只要每次转移状态逐渐累加就可以得到整个数组能偷取的钱。
step 2:(初始状态) 如果数组长度为1,只有一家人,肯定是把这家人偷了,收益最大,因此dp[1]=nums[0]dp[1] = nums[0]dp[1]=nums[0]。
step 3:(状态转移) 每次对于一个人家,我们选择偷他或者不偷他,如果我们选择偷那么前一家必定不能偷,因此累加的上上级的最多收益,同理如果选择不偷他,那我们最多可以累加上一级的收益。因此转移方程为dp[i]=max(dp[i−1],nums[i−1]+dp[i−2])dp[i] = max(dp[i - 1], nums[i - 1] + dp[i - 2])dp[i]=max(dp[i−1],nums[i−1]+dp[i−2])。这里的i在dp中为数组长度,在nums中为下标。
import java.util.*;public class Solution {/*** 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可** * @param nums int整型一维数组 * @return int整型*/public int rob (int[] nums) {// write code here//1.dp[i]表示长度为i的数组,最多能偷取多少钱(用dp[i]一维整型数组表示长度为i的数组,最多能偷取到多少钱,只要每次转移状态逐渐累加就可以得到整个数组能偷取的钱)int[] dp=new int[nums.length+1];//2.长度为1只能偷第一家(初始状态)如果数组长度为1,只有一家人肯定是把这家人偷了,利益最大,即dp[1]=nums[0]的情况。dp[1]=nums[0];//3.排除只有一家的情况外,根据整型数组nums的长度,遍历for(int i=2;i<=nums.length;i++)//4.对于每家可以选择偷或者不偷(状态转移)每次对于一个人家,我们选择偷他或者不偷它,如果我们偷那么前一家必定不能偷,因此累加的上上级的最多手机,同理如果选择不偷他,那我们最多可以累加上一级的收益。[简而言之,如果偷的话收益就是当前加的现金数加上上家之前所有偷的现金数的累加和。如果不偷的或就是不算上当前家的现金数,即为上家之前所有偷的现金的数]dp[i]=Math.max(dp[i-1],nums[i-1]+dp[i-2]);//5.最后返回当遍历完成后所偷的金钱数。return dp[nums.length];}
}

打家劫舍(二)
描述
你是一个经验丰富的小偷,准备偷沿湖的一排房间,每个房间都存有一定的现金,为了防止被发现,你不能偷相邻的两家,即,如果偷了第一家,就不能再偷第二家,如果偷了第二家,那么就不能偷第一家和第三家。沿湖的房间组成一个闭合的圆形,即第一个房间和最后一个房间视为相邻。
给定一个长度为n的整数数组nums,数组中的元素表示每个房间存有的现金数额,请你计算在不被发现的前提下最多的偷窃金额。

数据范围:数组长度满足 1≤n≤2×105 1 \le n \le 2\times10^5 \ 1≤n≤2×105 ,数组中每个值满足 1≤nums[i]≤5000 1 \le nums[i] \le 5000 \ 1≤nums[i]≤5000
示例1

输入:[1,2,3,4]
返回值: 6
说明:最优方案是偷第 2 4 个房间

示例2

输入: [1,3,6]
返回值: 6
说明:由于 1 和 3 是相邻的,因此最优方案是偷第 3 个房间

思路:

这道题与BM78.打家劫舍(一)比较类似,区别在于这道题是环形,第一家和最后一家是相邻的,既然如此,在原先的方案中第一家和最后一家不能同时取到

具体做法:

step 1:使用原先的方案是:用dp[i]表示长度为i的数组,最多能偷取到多少钱,只要每次转移状态逐渐累加就可以得到整个数组能偷取的钱。step 2:(初始状态) 如果数组长度为1,只有一家人,肯定是把这家人偷了,收益最大,因此dp[1]=nums[0]dp[1] = nums[0]dp[1]=nums[0]。step 3:(状态转移) 每次对于一个人家,我们选择偷他或者不偷他,如果我们选择偷那么前一家必定不能偷,因此累加的上上级的最多收益,同理如果选择不偷他,那我们最多可以累加上一级的收益。因此转移方程为dp[i]=max(dp[i−1],nums[i−1]+dp[i−2])dp[i] = max(dp[i - 1], nums[i - 1] + dp[i - 2])dp[i]=max(dp[i−1],nums[i−1]+dp[i−2])。这里的i在dp中为数组长度,在nums中为下标。step 4:此时第一家与最后一家不能同时取到,那么我们可以分成两种情况讨论:情况1:偷第一家的钱,不偷最后一家的钱。初始状态与状态转移不变,只是遍历的时候数组最后一位不去遍历。情况2:偷最后一家的请,不偷第一家的钱。初始状态就设定了dp[1]=0dp[1]=0dp[1]=0,第一家就不要了,然后遍历的时候也会遍历到数组最后一位。
import java.util.*;public class Solution {/*** 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可*** @param nums int整型一维数组* @return int整型*/public int rob (int[] nums) {// write code here//1.dp[i]表示长度为i的数组,最多能偷取多少钱(用dp[i]表示长度为i的数组,最多能偷取多少钱,只要每次转移状态逐渐累加就可以得到整个数组能偷取的钱)int[] dp = new int[nums.length + 1];//2.(初始状态)如果数组长度为1,只有一家人,肯定是把中家人偷了,收益最大,因此dp[i]=nums[0]-----选择偷第一家(Step 4总的情况1:偷第一家的的钱)dp[1] = nums[0];//3.排除第一家后,根据for循环遍历其余家是否可以偷,当然选择偷了第一家,最后一家不能偷(Step 4中情况1:初始状态和转移转台不变,知识遍历数组最后一位不取遍历)for (int i = 2; i < nums.length; i++)//4.对于每家可以选择偷或者不偷(状态转移)每次对于一个人家,我们选择偷他或者不偷他,如果我们选择偷那前一家必定能能偷,因此累加的上上级的最多收益,同理如果选择不偷他,那我们最多可以累加上一级收益。这里的i在dp中为数组的长度,在nums中为下标。dp[i] = Math.max(dp[i - 1], nums[i - 1] + dp[i - 2]);//5.将dp[]数组的结果赋值给整型resint  res = dp[nums.length - 1];//6.清除dp数组,第二循环Arrays.fill(dp, 0);//7.不偷第一家(step 4 中情况2:偷最后一家的钱,不偷最后一家的钱。即为初始状态就设定dp[1]=0,第一家就不要了)dp[1] = 0;//8.当不同最后一家,可以偷最后一家,然后for循环遍历,对于每家可以选择偷不偷(当偷最后一家是遍历的时候也会遍历数组的最后一位)for (int i = 2; i <= nums.length; i++)//9.对于每家可以选择偷或者不偷dp[i] = Math.max(dp[i - 1], nums[i - 1] + dp[i - 2]);//10.选择最大值return Math.max(res, dp[nums.length]);}
}

29、 打家劫舍(一)(二)相关推荐

  1. 2021年11月29日课二

    一.大数据时代究竟改变了什么--思维方式 (一).数据重要性 数据资源→数据资产(增值) (二).方法论 基于知识的理论完美主义(专家判断)→基于数据的历史经验主义 (三).数据分析 统计学(抽样)→ ...

  2. SSM开发书评网29:后台二:wangEditor图片上传;(主要内容是【wangEditor图片上传的文档要求】,【Spring MVC整合FileUpload组件,以实现文件上传功能】)

    说明: (1)本篇博客内容说明:[在后台系统,我们点击新增按钮后,会弹出新增图书对话框]→[该对话框中,包含一个wangEditor富文本编辑器]→[wangEditor富文本编辑器中,可以包含图片] ...

  3. 29 - 打家劫舍问题

    文章目录 1. 打家劫舍I 2. 打家劫舍II 3. 打家劫舍III (1) 暴力递归超时 (2) 记忆化搜索超时 (3) 动态规划 1. 打家劫舍I 动态规划: dp[i] = max(dp[i - ...

  4. 重庆“背篓夫妻”相伴29年 夫妻二人互为腿眼

    六十七岁老人再次演唱<大话西游>,点击后再看文章,更加应景 20日午后,微雨.江津区石门镇永安村,田地,房屋,鸡鸭,一切都静静的.一对老夫妻坐在家门前,认真编着背篓,一人编竹,一人编绳.没 ...

  5. 谷歌zxing 二维码生成工具

    一.加入maven依赖 <!-- 谷歌zxing 二维码 --> <dependency><groupId>com.google.zxing</groupId ...

  6. javascript实现二叉搜索树

    在使用javascript实现基本的数据结构中,练习了好几周,对基本的数据结构如 栈.队列.链表.集合.哈希表.树.图等内容进行了总结并且写了笔记和代码. 在 github中可以看到  点击查看,可以 ...

  7. java二维码生成-谷歌(Google.zxing)开源二维码生成学习及实例

    java二维码生成-谷歌(Google.zxing)开源二维码生成的实例及介绍  这里我们使用比特矩阵(位矩阵)的QR码编码在缓冲图片上画出二维码 实例有以下一个传入参数 OutputStream o ...

  8. 二十岁决定男人的一生

    第1节:完成三十岁前的积累,准备做一个成功的男人(1) Chapter Six 完成三十岁前的积累,准备做一个成功的男人  二十几岁是褪尽青涩,走向成熟的男人:二十几岁是很有紧迫感的年龄,如果男人到了 ...

  9. 华为M3平板升级鸿蒙系统,华为m3平板 日版刷国行 没有重力感应怎么解决?(篇二)...

    华为m3平板 日版刷国行 没有重力感应怎么解决?(篇二) 2020-01-13 20:21:39 12点赞 42收藏 29评论 篇二的理由华为m3平板 日版刷国行 没有重力感应怎么解决?小编注:此篇文 ...

最新文章

  1. Spring Cloud Alibaba 系统保护:微服务架构雪崩效应与服务限流
  2. XShell 技巧分享
  3. SOAP/Web Service/WSDL关系
  4. pgsql vs mysql查询_对比平台--SQL Server Vs PostgreSQL
  5. 关于Python的一些学习笔记(小白式笔记,持续更新)
  6. [BZOJ1036][ZJOI2008]树的统计Count(树链剖分)
  7. 浅谈细说 JS 函数(call,apply,重载)
  8. HTML5 浏览器返回按钮/手机返回按钮事件监听
  9. 第二章、使用变量、操作符和表达式
  10. S7-300中各个块之间的联系以及OB块的功能和应用场合
  11. 执行throw后 后面代码还会执行吗?
  12. Service的工作过程
  13. 如何实现微信小程序的横屏及适配
  14. 倾斜摄影超大场景的三维模型的顶层合并常见的问题分析
  15. 【二维前缀和】304. 二维区域和检索 - 矩阵不可变
  16. 关于Visual Assistant X助手在定位函数及结构体成员变量不准确的问题
  17. ASCII转十六进制小工具
  18. PreparedStatement 的 execute方法和executeUpdate方法区别
  19. css溢出影藏然后显示三个小点
  20. dell中小企业商用台式机Vostro4667 win10家庭中文版重装成win7版

热门文章

  1. matlab实现数字图像的加减乘除运算
  2. 【读点论文】Fawkes: Protecting Privacy against Unauthorized Deep Learning Models 添加像素扰动来实现图片的对抗AI识别
  3. 为什么在PCB设计制造中要使用DFM软件进行可制造性分析?
  4. 东北师范大学电子信息专硕(02)方向22年真题回忆版
  5. iphone12里的计算机,最简单:将iPhone 12投屏到电脑的最快方法
  6. windows10系统如何安装并配置jdk(亲测)
  7. 敏捷开发进度管理之燃尽图
  8. 【刷题】牛客网面试必刷TOP101
  9. 品甜蜜“醇时代”,享幸福“鑫品质”豫鑫糖醇盛装亮相2023生物发酵展
  10. 2021-05-25