DP:二维费用背包问题+似包非包

news2024/12/27 1:45:29

二维费用的背包问题:大多以01背包为基础,存在两个限制条件!

一、一和零

. - 力扣(LeetCode)

class Solution {
public:
//需要满足两个条件的我们称之为二位费用的背包问题
    int findMaxForm(vector<string>& strs, int m, int n) {
         //dp[i][j][k]表示前i个字符串中选  0不超过j  1不超过k
         //str[i-1]有a个0,b个1  
         //如果不选i  dp[i][j][k]=dp[i-1][j][k]
         //如果选i dp[i][j][k]=dp[i-1][j-a][k-b]+1 
         int len=strs.size();
         vector<vector<vector<int>>> dp(len+1,vector<vector<int>>(m+1,vector<int>(n+1)));
         for(int i=1;i<=len;++i)
          {
             //先统计一下其数量
             int a=0,b=0;
             for(auto&ch:strs[i-1])
             if(ch=='0') ++a; else ++b;
             for(int j=0;j<=m;++j)  //只要保证i是从小到大的即可 j和k无所谓 因为会用到的是i-1那一面的值
               for(int k=0;k<=n;++k)
                {
                    dp[i][j][k]=dp[i-1][j][k];
                    if(j>=a&&k>=b) dp[i][j][k]=max(dp[i][j][k],dp[i-1][j-a][k-b]+1);
                }
          }
          return dp[len][m][n];
    }
};

 滚动数组优化一个维度

class Solution {
public:
    int findMaxForm(vector<string>& strs, int m, int n) {
          //dp[i][j][k]表示前i个字符串中选  0不超过j  1不超过k
         //str[i-1]有a个0,b个1  
         //如果不选i  dp[i][j][k]=dp[i-1][j][k]
         //如果选i dp[i][j][k]=dp[i-1][j-a][k-b]+1 
         int len=strs.size();
        vector<vector<int>> dp(m+1,vector<int>(n+1));
         for(int i=1;i<=len;++i)
          {
             //先统计一下其数量
             int a=0,b=0;
             for(auto&ch:strs[i-1])
             if(ch=='0') ++a; else ++b;
             for(int j=m;j>=a;--j)  //空间优化后要保证从大往小遍历
               for(int k=n;k>=b;--k)
                   dp[j][k]=max(dp[j][k],dp[j-a][k-b]+1);
          }
          return dp[m][n];
    }
};

 二、盈利计划(非常经典)

. - 力扣(LeetCode)

class Solution {
public:
    int profitableSchemes(int n, int m, vector<int>& g, vector<int>& p) {
        //01背包问题 一个工作可以选择做或者不做profit  两个限制条件 一个是minProfit 一个是n
        //dp[i][j][k] 从前i个工作中选 人数要不超过j 利润至少为k 的所有选择计划。
        const int MOD=1e9+7;
        int len=g.size();
        vector<vector<vector<int>>> dp(len+1,vector<vector<int>>(n+1,vector<int>(m+1)));
        //如果不做i工作 dp[i][j][k]=dp[i-1][j][k]
        //如果做了i工作 dp[i][j][k]+=dp[i-1][j-g[i-1]][k-p[i-1]]
        //分析初始化 如果i为0时 显然都为0 p为0时 有j=1
        for(int j=0;j<=n;++j) dp[0][j][0]=1; //完成初始化 只需考虑i为0的情况即可 因为其他都会特判
        //开始填表
        for(int i=1;i<=len;++i) //只需考虑i即可
          for(int j=0;j<=n;++j) 
            for(int k=0;k<=m;++k)
            {
                dp[i][j][k]=dp[i-1][j][k];
                if(j>=g[i-1]) dp[i][j][k]+=dp[i-1][j-g[i-1]][max(k-p[i-1],0)];
                dp[i][j][k]%=MOD;
            }
            return dp[len][n][m];
       
    }
};

滚动数组优化维度:

class Solution {
public:
    int profitableSchemes(int n, int m, vector<int>& g, vector<int>& p) {
         //01背包问题 一个工作可以选择做或者不做profit  两个限制条件 一个是minProfit 一个是n
        //dp[i][j][k] 从前i个工作中选 人数要不超过j 利润至少为k 的所有选择计划。
        const int MOD=1e9+7;
        int len=g.size();
        vector<vector<int>> dp(n+1,vector<int>(m+1));
        //如果不做i工作 dp[i][j][k]=dp[i-1][j][k]
        //如果做了i工作 dp[i][j][k]+=dp[i-1][j-g[i-1]][k-p[i-1]]
        //分析初始化 如果i为0时 显然都为0 p为0时 有j=1
        for(int j=0;j<=n;++j) dp[j][0]=1; //完成初始化 只需考虑i为0的情况即可 因为其他都会特判
        //开始填表
        for(int i=1;i<=len;++i) //只需考虑i即可
          for(int j=n;j>=g[i-1];--j) 
            for(int k=m;k>=0;--k)
            {
                dp[j][k]+=dp[j-g[i-1]][max(k-p[i-1],0)];
                dp[j][k]%=MOD;
            }
            return dp[n][m];
    }
};

 三、组合总和IV(似包非包)

. - 力扣(LeetCode)

分析问题的过程中,发现重复子问题,然后抽象出一个状态表示

class Solution {
public:
//该题是排列总和 
//背包问题本质上解决的是  有限制条件的组合问题
    int combinationSum4(vector<int>& nums, int target) {
        vector<double> dp(target + 1);
        dp[0] = 1;
        for (int i = 1; i <= target; i++) 
            for (int& num : nums) 
                if (num <= i) dp[i] += dp[i - num];
        return dp[target];
    }
};

四、不同的二叉搜索树(卡特兰数)

. - 力扣(LeetCode)

class Solution {
public:
    int numTrees(int n) {
        vector<int> dp(n+1);
        dp[0]=1;//dp[i]表示i个节点时有多少种搜索树
        for(int i=1;i<=n;++i)
          for(int j=1;j<=i;++j)
            dp[i]+=dp[j-1]*dp[i-j];
        return dp[n];
        //发现重复子问题,抽象出一种状态表示
    }
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1855347.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

在 IntelliJ IDEA 中使用 Java 和 Selenium 模拟 Chrome 浏览器教程

在 IntelliJ IDEA 中使用 Java 和 Selenium 模拟 Chrome 浏览器教程 1. 前言2. 环境准备3. 关闭谷歌自动更新通过服务禁用更新服务通过任务计划程序禁用更新任务 4. 项目添加 Maven 依赖项5. 编写自动化脚本6. 项目运行效果7. 代码示例8.常用方法示例页面请求定位标签获取内容操…

Python低溫半导体电子束量子波算法计算

&#x1f3af;要点 &#x1f3af;任意维度求解器&#xff0c;绘制三维投影结果 | &#x1f3af;解二维静电场、静磁场 | &#x1f3af;狄利克雷、诺依曼条件几何矩阵算子 | &#x1f3af;算法模拟低溫半导体材料 | &#x1f3af;计算曲面达西流 | &#x1f3af;电子结构计算和…

学习VXLAN -- 报文结构、原理和配置

目录 VXLAN背景什么是VXLANVXLAN的优势VXLAN报文结构一些特定名词BDVBDIFVAPVSIVSI-InterfaceAC VXLAN的实现原理图VXLAN MAC地址表项MAC地址动态学习 VXLAN隧道VXLAN隧道工作模式L2 GatewayIP Gateway VXLAN隧道的建立与关联VXLAN隧道建立的方式VXLAN对到与VXLAN关联的方式 配…

系统思考与创新解决

圆满结束了为期两天的《系统思考》课程。在这次学习中&#xff0c;大家积极使用系统环路图来分析并呈现跨部门的业务协同问题&#xff0c;以及探讨了推动成长环路背后的限制因素。这不仅增强了团队之间的理解和合作&#xff0c;也帮助我们一起识别阻碍组织发展的关键挑战。期待…

obsidian中用check list 打造待办清单

背景 在快节奏的现代生活中&#xff0c;有效管理个人时间和任务成为提升生活与工作效率的关键。 Obsidian&#xff0c;作为一款强大的知识管理和笔记应用&#xff0c;通过其丰富的插件生态&#xff0c;为我们提供了高度自定义的任务管理解决方案。本文旨在详细介绍如何在Obsid…

AI应用带你玩系列之SadTalker

前段时间我刷微信视频&#xff0c;我无意间点开了一个&#xff0c;画面缓缓展开&#xff0c;是一幅精致的水墨画&#xff0c;画中人物皆是古代装束&#xff0c;衣袂飘飘&#xff0c;仿佛能闻到墨香。然而&#xff0c;这宁静的画面突然被打破了&#xff0c;画中的人物开始动了起…

自动驾驶仿真Carla -ACC功能测试

我将详细说明如何使用Carla进行ACC&#xff08;自适应巡航控制&#xff09;测试&#xff0c;确保每个步骤贴合实际的Carla自动驾驶仿真标准&#xff0c;并提供相应的代码示例。 使用Carla进行ACC测试的步骤&#xff1a; 1. 环境设置和启动Carla 首先&#xff0c;确保你已经安装…

在vue项目中集成cesium

首先创建一个新的vue项目 安装vite中cesium插件 https://github.com/nshen/vite-plugin-cesium 安装插件 npm i cesium vite-plugin-cesium vite -D配置插件 注释原有样式 修改代码 效果

重学java 79.JDK新特性 ⑤ JDK8之后的新特性

别怕失败&#xff0c;大不了重头再来 —— 24.6.20 一、接口的私有方法 Java8版本接口增加了两类成员: 公共的默认方法 公共的静态方法 Java9版本接口又新增了一类成员: 私有的方法 为什么IDK1.9要允许接口定义私有方法呢? 因为我们说接口是规范&#xff0c;规范是…

AI 大模型企业应用实战(08)-LangChain用prompts模板调教LLM的输入输出

超越chatGPT:学习使用prompts模板来调教LLM的输入输出&#xff0c;打造自己版本的"贾维斯" 1 Model I/O&#xff1a;LLM的交互接口 任何语言模型应用程序的核心要素都是......模型。LangChain 为您提供了与任何语言模型连接的构件。 即 Prompts -> Language mod…

免费ddns工具,快解析DNS解析使用教程

DDNS&#xff08;Dynamic Domain Name Server&#xff09;,中文叫动态域名解析&#xff0c;主要用于没有固定公网ip的网络环境下&#xff0c;使用一个固定的域名&#xff0c;解析动态变化的ip地址&#xff0c;达到远程访问的目的。 众所周知&#xff0c;目前公网ip资源非常紧缺…

昇思25天学习打卡营第6天|使用静态图加速

学AI还能赢奖品&#xff1f;每天30分钟&#xff0c;25天打通AI任督二脉 (qq.com) 背景介绍 AI编译框架分为两种运行模式&#xff0c;分别是动态图模式以及静态图模式。MindSpore默认情况下是以动态图模式运行&#xff0c;但也支持手工切换为静态图模式。两种运行模式的详细介…

MySQL数据库(三):读取数据库数据

上一节&#xff0c;我们介绍了数据库的基本操作&#xff0c;以及最后演示了如何使用库来连接数据库&#xff0c;在实际应用中&#xff0c;我们通常需要按照指定的条件对数据库进行操作&#xff0c;即增删改查操作&#xff0c;这是非常重要的&#xff01;这一节我们继续通过一个…

【电源专题】案例:电量计遇到JEITA充电芯片,在高温下无法报百怎么办?

在使用电量计芯片时,我们期望的是在产品工作温度下、在产品最低和正常充电电流下都要能报百。 所谓报百,就是电量计RSOC(电量百分比)能到达100%。这看起来简单,如果是常规的操作的话,那么电压达到充电截止要求、电流达到充电截止要求、容量累积变化满足要求,RSOC=100%肯…

数据清洗!即插即用!异常值、缺失值、离群值处理、残差分析和孤立森林异常检测,确保数据清洗的全面性和准确性,MATLAB程序!

适用平台&#xff1a;Matlab2021版及以上 数据清洗是数据处理和分析中的一个关键步骤&#xff0c;特别是对于像风电场这样的大型、复杂数据集。清洗数据的目的是为了确保数据的准确性、一致性和完整性&#xff0c;从而提高数据分析的质量和可信度&#xff0c;是深度学习训练和…

面向卫星遥感的红外微小舰船目标检测方法:MTU-Net

论文简介 空间红外微小舰船检测旨在从地球轨道卫星所拍摄的图像中识别并分离出微小舰船。由于图像覆盖面积极其广大&#xff08;如数千平方公里&#xff09;&#xff0c;这些图像中的候选目标相比空中或地面成像设备观测到的目标&#xff0c;尺寸更小、亮度更低且变化更多。现有…

详细分析Springmvc中的@ModelAttribute基本知识(附Demo)

目录 前言1. 注解用法1.1 方法参数1.2 方法1.3 类 2. 注解场景2.1 表单参数2.2 AJAX请求2.3 文件上传 3. 实战4. 总结 前言 将请求参数绑定到模型对象上&#xff0c;或者在请求处理之前添加模型属性 可以在方法参数、方法或者类上使用 一般适用这几种场景&#xff1a; 表单…

图形编辑器基于Paper.js教程03:认识Paper.js中的所有类

先来认一下Paper的资源对象&#xff0c;小弟有哪些&#xff0c;有个整体的认识。认个脸。 在Paper.js的 官方文档中类大致有如下这些&#xff1a; 基类&#xff1a; ProjectViewItemPointToolSizeSegmentRectangleCurveCurveLocationMatrixColorStyleTweenToolEventGradient…

用于射频功率应用的氮化铝电阻元件

EAK推出了新的厚膜氮化铝 &#xff08;AlN&#xff09; 电阻器和端接系列&#xff0c;以补充公司现有的产品。传统上&#xff0c;射频功率电阻元件采用氧化铍&#xff08;BeO&#xff09;陶瓷材料作为陶瓷基板;然而&#xff0c;由于国际上要求从产品中去除BeO的压力&#xff0c…

26.3 Django路由层

1. 路由作用 在Django中, URL配置(通常称为URLconf)是定义网站结构的基础, 它充当着Django所支撑网站的目录. URLconf是一个映射表, 用于将URL模式(patterns)映射到Python的视图函数或类视图上. 这种映射机制是Django处理HTTP请求的基础, 它决定了当客户端发送请求时, Django如…