导言
部分背包问题
0 1 背包问题
完全背包问题
多重背包问题
背包的分类
一级包,二级包和三级包,显然其中三级包的容量是最大的,吃鸡必备装备啊!
但是我们需要研究的是这样的问题:
各种背包
背包问题大概分下面这几种
- 部分背包问题
- 0 1 背包问题
- 完全背包问题
- 多重背包问题
问题
为什么要学习背包问题呢?
- 背包问题已经是一个很经典而且讨论很广泛的算法问题了。
- 背包问题的解决方法背后其实隐藏了两种我们比较常见的算
法解决思路,动态规划和贪心算法。
部分背包
定义:
部分背包问题:
给出 n 个物体,第 i 个物体重量为 wi, 价值为 vi。在总重量
不超过 W 的情况下让总价值尽量高,每一个物体都可以只取走
一部分,价值和重量按比例计算。
分析
因为物体既有重量又有价值,所以不能简单的先拿轻的 (轻
的可能价值也小),也能先拿价值大的 (它可能特别重),而因该
综合考虑两个因素。一种直观的贪心策略就是:优先拿“价值除
以重量”最大的,直到重量和正好为 W
那么你作为一个非常优秀的 ACMer,肯定应该知道按照什
么顺序拿物品的把。没错,看着值钱的先抢!
那么问题很简单咯 ,把” 值钱” 的东西排在前面,每次拿抢
的时候,问问看背包君够不够承受得住,承受的了,就全部抢过
来。承受不住,那么只能按照所能承受的重量,取物品的一部分
了。当然价值也得按照比例来哦
部分背包没什么好讲的,主要是一个贪心策略,就是优先选取性价比最高的来装入背包
01背包
0 1 背包问题:
有 n 种重量和价值分别为 wi ,vi 的物品,从这些物品中挑选
总重量不超过 W 的物品,求出挑选物品价值总和的最大值。在
这里,每种物品只可以挑选一件
限制条件
- 1≤n≤100 1 ≤ n ≤ 100
- 1≤wi;vi≤100 1 ≤ w i ; v i ≤ 100
- 1≤W≤10000 1 ≤ W ≤ 10000
分析一下
这道题就是各个物品“选”与“不选”的组合,因此被称为0−1背包问题 这 道 题 就 是 各 个 物 品 “ 选 ” 与 “ 不 选 ” 的 组 合 , 因 此 被 称 为 0 − 1 背 包 问 题 如果检查n个物品所有“选”与“不选”的组合 如 果 检 查 n 个 物 品 所 有 “ 选 ” 与 “ 不 选 ” 的 组 合
算法的复杂度为O(2n) 算 法 的 复 杂 度 为 O ( 2 n ) 当物品的大小以及背包的大小均为正数 当 物 品 的 大 小 以 及 背 包 的 大 小 均 为 正 数
则0−1背包问题可以用动态规划法以O(nW)的效率解决。 则 0 − 1 背 包 问 题 可 以 用 动 态 规 划 法 以 O ( n W ) 的 效 率 解 决 。
状态转移方程:
如果我们按照如下的方式来定义递推关系的话,刚刚关于i的循环就能正向进行 如 果 我 们 按 照 如 下 的 方 式 来 定 义 递 推 关 系 的 话 , 刚 刚 关 于 i 的 循 环 就 能 正 向 进 行
我们定义dp[i+1][j]:=从0到i这i+1个物品中选出总重量不超过 j 的物品时总价值的最大值 我 们 定 义 d p [ i + 1 ] [ j ] := 从 0 到 i 这 i + 1 个 物 品 中 选 出 总 重 量 不 超 过 j 的 物 品 时 总 价 值 的 最 大 值
很显然dp[0][j]=0,因为你没物品可取的时候背包的价值为0 很 显 然 d p [ 0 ] [ j ] = 0 , 因 为 你 没 物 品 可 取 的 时 候 背 包 的 价 值 为 0
所以我们可以写出下边的状态转移方程