动态规划算法学习三:0-1背包问题

news2024/11/20 2:43:39

文章目录

  • 前言
  • 一、问题描述
  • 二、DP解决步骤
    • 1、最优子结构性质
    • 2、状态表示和递推方程
    • 3、算法设计与分析
    • 4、计算最优值
    • 5、算法实现
    • 6、缺点与思考

前言

一、问题描述

在这里插入图片描述
在这里插入图片描述

二、DP解决步骤

1、最优子结构性质

在这里插入图片描述

2、状态表示和递推方程

  • 子问题可由两个参数确定:待考虑装包的物品集背包的容量
  • 将所有物品按照1至n 标号,待考虑装包的物品集可以用物品集中末尾物品的标号来描述,则得状态表示𝑽𝒂𝒍(𝒊,𝒑),1≤𝑖≤𝑛, 0≤𝑝≤𝐶 表示在背包容量为𝑝,待考虑装包的物品集为{1, 2, …, i}时的最大装入物品价值。
  • Val(n, C) 则表示原问题的最优解。

3、算法设计与分析

𝑽𝒂𝒍(𝒊,𝒑),1≤𝑖≤𝑛, 0≤𝑝≤𝐶 表示在背包总容量𝑝,待考虑装包的物品集为{1, 2, …, i} 时的最大装入物品价值。
在这里插入图片描述

解释上图:

  • 当 i = 1时:
    • 如果w1 > p,说明放不下背包,则价值为 0;
    • 如果w1 < p,则能放进去,且价值为 v1
  • 当 i > 1时:
    • 如果wi > p 时,说明,整个包都放不下一个第i个物品,则这个物品可以舍弃,且价值为之前的i-1的价值 即:Val(i - 1,p)
    • 如果wi < p时,说明,这个包是可以放得进去背包的,则需要判断值不值的:
      整个包能放下第i个物品,只有两种可能性:
      1. 不放第i个物品:价值仍然是val(i-1,p)
      2. 放入第i个物品:包中需要为其腾出 wi 的空;那么前i-1个物品就只能从p-wi 的空中选取最佳组合,其最佳组合值为 val(i-1,p-wi) ;然后再加上vi
      然后,对这两种可能的子问题的最优值进行max;
      注意:前i-1个物品在不同的包容量Px下,其组合都是不同的,但是最佳值都可以用val(i-1,Px)来表示。在自底向上方法下,Px可以逐步累加,来求解val(i-1,Px)的值。

4、计算最优值

在这里插入图片描述
在这里插入图片描述

按物品的两种基本单位来给出表格的行数和列数,而不是根据物品的数目和价值!有枚举的意思,回顾暴力算法章节中剪绳子的问题!
3-6处的9:能放进去,但价值会降低,不腾,不放
3-8处的11:能放进去,但要腾1个,价值会升高,腾,放
3-10处的14:能放进去,但剩余空间够,不必腾,放,价值会升高

在这里插入图片描述

按照上面公式以及逻辑计算:

  1. i = 1时,有11个情况,0-10,
    物品只有第一个,n=1;
    只有 p = 2及以后, p>=(w1 = 2),v1 = 6,所以背包从 2 开始到 10 都是 6
    (这里是第一个公式,往后就只使用第二个公式进行比较)
  2. i = 2时,11个情况,0-10
    物品是前2个,n=2;
    p = 2时,满足p >= (w2 = 2),可以替换,但需要比较 是否值得替换:Val(i-1, p)=Val(1,2)=6,Val(i-1, p - w2)+v2= Val(1,0)+3 = 3,3<;虽然能替换,放了还不如原来的价值,所以不替换。背包放 1 号物品;
    p = 3时,同上。
    p = 4时及以后(从逻辑上讲:背包放1号和2号物品,即9 正好,但是也需要计算)。p > (w2 = 2),可以放,但需要比较 是否值得放:Val(i-1, p)=Val(1,4)=6,Val(i-1, p - w2)+v2= Val(1,2)+3 = 9,9>6,则可以放。
  3. i = 3时,11个情况,0-10
    物品有3个,n=3;
    p = 2时,同上面的 p = 2 的逻辑。放物品1
    p = 4时,同上面的 p = 4 的逻辑。放物品1,2
    p = 8时,p >= (w3 = 6),可以替换,但需要比较 是否值得替换:Val(i-1, p)=Val(2,8)=9,Val(i-1, p - w3)+v3= Val(2,2)+5 = 11,11>9,所以可以替换。把n=2拿出来,把n=3放进去,权重相加等于8,价值为11;放物品1,3
    p = 10时,p >= (w3 = 6),可以替换,但需要比较 是否值得替换 :Val(i-1, p)=Val(2,10)=9,Val(i-1, p - w3)+v3= Val(2,4)+5 = 14。三个都可以放进去,则价值为14。放物品1,2,3
  4. i = 4时,11个情况,0-10
    物品有4个,n=4;
    p = 2时,同上面的 p = 2 的逻辑。放物品1
    p = 4时,同上面的 p = 4 的逻辑。放物品1,2
    P = 7时,p >= (w4 = 5),可以替换,但需要比较 是否值得替换 ,Val(i-1, p)=Val(3,7)=9,Val(i-1, p - w4)+v4= Val(3,2)+4 = 10,因为 9 < 10,所以可以放。放物品1,4
    P = 8时,p >= (w4 = 5),可以替换,但需要比较 是否值得替换 ,Val(i-1, p)=Val(3,8)=11,Val(i-1, p - w4)+v4= Val(3,3)+4 = 10,因为 11 > 10,所以替换,放物品1,3
    P = 9时,p >= (w4 = 5),可以替换,但需要比较 是否值得替换 ,Val(i-1, p)=Val(3,9)=11,Val(i-1, p - w4)+v4= Val(3,4)+4 = 13,因为 11 < 13 ,所以替换,放物品1,2,4
    P = 10时,p >= (w4 = 5),可以替换,但需要比较 是否值得替换 ,Val(i-1, p)=Val(3,10)=14,Val(i-1, p - w4)+v4= Val(3,5)+5 = 14,因为 14 = 14 ,所以替换,存物品1,2,3
  5. i = 5时,11个情况,0-10
    物品有5个,n=5;

5、算法实现

import java.util.Arrays;

import static java.lang.Math.max;

/**
 * DP之0-1背包问题
 */
public class Main3 {

    public static int MaxN = 11;
    public static int MaxC = 11;

    public static void main(String[] args) {
        int[] w = {2, 2, 6, 5, 4};
        double[] v = {6, 3, 5, 4, 6};
        double v1 = binaryKnapsack(w.length, w, v, 10);
        System.out.println(v1);
    }

    public static double binaryKnapsack(int numItems, int[] w, double[] v, int capacity) {
        double[][] val = new double[numItems][capacity + 1];
        memSet(val, 0, val.length);

        for (int i = 1; i < numItems; i++)
            for (int j = 0; j <= capacity; j++) {
                val[i][j] = val[i - 1][j];
                if (j >= w[i])
                    val[i][j] = max(val[i - 1][j], val[i][j - w[i]] + v[i]);
            }

        // 打印二维数组
        for (int i = 0; i < val.length; i++) {
            System.out.println(Arrays.toString(val[i]));
        }
        return val[numItems - 1][capacity]; // [4][10]
    }

    public static void memSet(double[][] val, int col, int length) {
        for (int i = 0; i < length; i++) {
            for (int j = 0; j < val[i].length; j++){
                val[i][j]=0;
            }
        }
    }

}

计算 𝑣𝑎𝑙(𝑖,𝑝)的值只需要Val数组中第𝒊−𝟏行中第𝑝个分量之前的数值。

6、缺点与思考

在这里插入图片描述

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

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

相关文章

【C/调试实用技巧】—作为程序员应如何面对并尝试解决Bug?

小菜坤日常上传gitee代码&#xff1a;https://gitee.com/qi-dunyan 关于C语言的所有由浅入深的知识&#xff0c;都存放在专栏【c】 ❤❤❤ 个人简介&#xff1a;双一流非科班的一名小白&#xff0c;期待与各位大佬一起努力&#xff01; 推荐网站&#xff1a;cplusplus.com 目录…

Springboot集成ItextPdf

目录 一、概述 二、Itext API 1.PDF文档生成 3.常用对象 一、文档对象 二、操作对象 三、内容对象 四、表格对象 四、常用案例 一、水印 三、页眉页脚 四、合并多个PDF 五、表单PDF 六、模板PDF 一、html模板 二、使用工具构建PDF模板 7、HTML转PDF 8、删除页…

同花顺_知识_庄家技法_4拉升技法

写在前面&#xff1a; 文中知识内容来自书籍《同花顺炒股软件从入门到精通》 目录 1. 拉升时机的选择 1&#xff09;大盘走势稳健时 2&#xff09;重大利好出台前后 3&#xff09;进行一次凶狠的打压之后 4&#xff09;大市偏弱时 5&#xff09;图形及技术指标修好之时 …

FPGA开发(4)——AXI_LITE总线协议

一、AXI总线简介 对于axi总线的学习我主要是参考了赛灵思的ug1037文档以及arm的INI0022D手册&#xff0c;对其中的内容做了总结。 AXI是amba总线的一种&#xff0c;包含三种&#xff0c;axi full、axi lite和axi stream。 AXI工作&#xff1a;axi接口包含了五组通道&#xf…

如何快速用一条命令配置好本地yum源(6/7/8版本)

一&#xff0c;挂载ISO安装镜像 挂载方式分两种&#xff1a; 1.上传iso安装镜像到服务器主机的指定目录&#xff0c;比如/setup/os为例 mount -o loop /setup/os/iso镜像包名称 /mnt 2.直接虚拟机或者物理主机挂载iso安装镜像 mount /dev/cdrom /mnt mount/dev/sr0 /mnt 3.挂载…

【计算机网络】网络层:路由器的构成

路由器工作在网络层&#xff0c;用于互连网络&#xff0c;主要工作是转发分组。 把某个输入端口收到的分组&#xff0c;按照分组要去的目的网络&#xff0c;把该分组从路由器的某个合适的输出端口转发给下一跳路由器。 &#xff08;根据目的网络的IP地址转发分组&#xff09;…

[附源码]java毕业设计学生档案管理系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

使用Umi 遇到的错误

今天想使用ui&#xff0c;出现了很多错误&#xff0c;刚开始安装的时候没有一点事&#xff0c;就是运行的时候报错&#xff0c;好像和umi版本不匹配了&#xff0c;后来又把umi删除了又安装一遍&#xff0c;然后还是运行不了&#xff0c;后来我又把umijs/preset-ui卸了&#xff…

通过制作4个游戏学习Python

前言 学习编程最好玩的方法 你会学到什么 &#xff08;文末送读者福利&#xff09; 您将学习如何有效地使用Python 您将创建一个python游戏组合 你将学会如何管理好大型项目 你将学习面向对象编程 您将学习并实现高级Python特性 你将对Python有一个透彻的理解 类型:电…

Spark并行度和任务调度

文章目录并行度如何设置并行度如何规划我们自己群集环境的并行度&#xff1f;Spark的任务调度并行度 Spark之间的并行就是在同一时间内&#xff0c;有多少个Task在同时运行。并行度也就是并行能力的设置&#xff0c;假设并行度设置为6&#xff0c;就是6个task在并行跑&#xf…

蒙特卡洛原理及实例(附Matlab代码)

文章目录一、理论基础1.1 伯努利大数定理1.2 辛钦大数定理1.3 切比雪夫大数定理1.4 三者区别和联系二、蒙特卡洛法2.1 蒙特卡洛的起源2.2 蒙特卡洛的解题思路2.2 蒙特卡洛法的应用三、几个小栗子3.1 求解定积分3.1.1 解析法3.1.2 蒙特卡洛法3.2 求解六边形面积3.2.1 解析法3.2.…

[附源码]SSM计算机毕业设计基于的高校学生考勤管理系统JAVA

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

支持向量机

目录 支持向量机 0. 由来 1. 核心思想 2. 硬间隔支持向量机 2.1 间隔最大化 2.1.1 函数间隔2.1.2 几何间隔2.1.2 间隔最大化 2.2 转换为拉格朗日对偶问题 2.2.1 拉格朗日对偶问题2.2.2 将问题转换为拉格朗日对偶问题 3. 软间隔支持向量机 4. 泛函基础 4.1 度量&#xff…

Flutter 8 个优秀动画 Packages

Flutter 8 个优秀动画 Packages 前言 动画对于使移动应用程序的用户界面感觉自然流畅至关重要。加上交互式元素和平滑的过渡&#xff0c;它们使应用程序简单易用。 正文 Flutter Animate 组件 Package https://pub.dev/packages/flutter_animate 一个 performant 库&#xff0c…

springboot simple (9) springboot jpa(Hibernate)

返回目录 1 JPA Hibernate Hibernate是一个全自动的ORM框架&#xff08;Object Relational Mapping ,对象关系映射&#xff09;。 Spring Data JPA&#xff1a; 是Spring Data的子模块&#xff0c;JPA默认使用hibernate作为ORM实现。 2 springboot继承Hibernate 第1步&…

【Servlet】7:监听器和过滤器的原理和应用

目录 | 监听器 监听器 基本概述 ServletContextListener监听器 ServletContextAttributeListener监听器 监听器的应用场景 | 过滤器 过滤器 基本概述 过滤器 实现步骤 过滤器 应用场景 本文章属于后端全套笔记的第三部分 &#xff08;更新中&#xff09;【后端入门到入…

leetcode 494.目标和 动态规划背包问题 (c++版本)

题目描述 说白了就是让一部分数减去剩下的一部数使得差值为target&#xff0c;计算有多少中组合的方法 下面来个数学公式推导一下 leftrightsumleft−righttargetleftsum−lefttargetleft(sumtarget)/2leftright sum\\ left-righttarget\\ leftsum-lefttarget\\ left(sumtarge…

用户行为分析-如何用数据驱动增长

用户行为分析-如何用数据驱动增长 2022-11-22 看完书才知道是 GrowingIO 公司出的一本书&#xff0c;干货还是挺多的。 第一章从商业进化的角度认识用户行为数据的重要性&#xff0c;帮助大家了解什么是用户行为数据&#xff0c;以及用户行为数据怎么发挥价值。接着四章详细…

【操作系统】2.2 操作系统的调度

2.2.1 操作系统之处理机调度的概念及层次 2.2.1操作系统之处理机调度的概念及层次_StudyWinter的博客-CSDN博客_操作系统调度的层次 高级调度&#xff08;作业调度&#xff09;&#xff1a;外存-》内存 中级调度&#xff08;内存调度&#xff09;&#xff1a;外存-》内存 低…

用最少的代码模拟gRPC四种消息交换模式

我们知道&#xff0c;建立在HTTP2/3之上的gRPC具有四种基本的通信模式或者消息交换模式&#xff08;MEP&#xff1a; Message Exchange Pattern&#xff09;&#xff0c;即Unary、Server Stream、Client Stream和Bidirectional Stream。本篇文章通过4个简单的实例演示它们在.NE…