一、问题描述

物品无限的背包问题:有n种物品,每种均有无穷多个。第 i 种物品的体积为Vi,重量为Wi。选一些物品装到一个容量为 C 的背包中,求使得背包内物品总体积不超过C的前提下重量的最大值。1≤n≤100, 1≤Vi≤C≤10000, 1≤Wi≤1000000.

二、解题思路

我们可以先求体积恰好为 i 时的最大重量(设为d[i]),然后取d[i]中的最大值(i ≤ C)。与之前硬币问题,“面值恰好为S”就类似了。只不过加了新属性——重量,相当于把原来的无权图改成带权图,即把“+1”变成“+W[j]”。这样,问题就变成了求以C为起点、终点任意的,边权之和最大的路径。

三、代码实现

1、记忆化搜索

之前纠结这种方法的时间复杂度,先给结果:O(maxn * maxc)。因为计算dp(s)时,如果dp[i]中i是从0-->C,

则dp[i] = max(dp[i],dp[i - V[j]] + W[j]),dp[i - V[j]]已经计算出来且保存,相当于得到dp[i]没有花费时间。如果dp[i]中i是从C-->0,

每次计算的都被保存且只计算一次,有几次小的递归,也相当于没有花费时间。

 #include<stdio.h>
#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std; const int INF = 0x3f3f3f3f;
const int maxn = + ;
const int maxc = + ;
int n,V[maxn],W[maxn],C;
int d[maxc]; //d[i]表示总体积恰好为i时的最大重量 int dp(int s)
{
int& ans = d[s];
if (ans != -) return ans;
ans = - INF;
for (int i = ; i < n; i++)
{
if (s >= V[i]) ans = max(ans, dp(s - V[i]) + W[i]);
}
return ans;
}
void slove()
{
memset(d, -, sizeof(d));
d[] = ;
int res = -;
for (int i = 0; i <= C; i++)
res = max(res, dp(i));
printf("%d\n", res);
} int main()
{
while (scanf("%d",&n) == && n)
{
scanf("%d", &C);
for (int i = ; i < n; i++)
scanf("%d%d", &V[i], &W[i]); slove();
}
return ;
}

2、递推式

这种写法时间复杂度十分显然,与记忆化搜索相同,都是O(maxn * maxc)。但必须注意循环的顺序,比如容量只能从0-->C,而不能反过来,前一种写法则没有循环的顺序要求。

 void slove()
{
fill(d, d + n, -INF);
d[] = ;
int res = -;
for (int i = ; i <= C; i++) //容量的循环顺序只能是从小到大
{
for (int j = ; j < n; j++)
{
if(i >= V[j]) d[i] = max(d[i], d[i - V[j]] + W[j]);
}
res = max(res, d[i]);
}
printf("%d\n", res);
}

3、两者比较

在得到状态转移方程之后,还需要思考如何编写程序。尽管在很多情况下,记忆化搜索程序更直观、易懂,但在0-1背包中递推法更理想。因为已知状态转移方程后,递推法的难点是循环顺序,而有了“阶段”定义后,循环顺序变得十分显然。

由DAG到背包问题——记忆化搜索和递推两种解法的更多相关文章

  1. UVA_437_The_Tower_of_the_Babylon_(DAG上动态规划/记忆化搜索)

    描述 https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&a ...

  2. ACM/ICPC 之 简单DP-记忆化搜索与递推(POJ1088-滑雪)

    递推型DP 将每个滑雪点都看作起点,从最低点开始逐个由四周递推出到达此点的最长路径的长度,由该点记下. 理论上,也可以将每一点都看作终点,由最高点开始计数,有兴趣可以试试. //经典DP-由高向低海拔 ...

  3. 专题1:记忆化搜索/DAG问题/基础动态规划

      A OpenJ_Bailian 1088 滑雪     B OpenJ_Bailian 1579 Function Run Fun     C HDU 1078 FatMouse and Chee ...

  4. LightOJ1417 Forwarding Emails(强连通分量+缩点+记忆化搜索)

    题目大概是,每个人收到信息后会把信息发给他认识的一个人如此下去,问一开始要把信息发送给谁这样看到信息的人数最多. 首先找出图中的SCC并记录每个SCC里面的点数,如果传到一个SCC,那么里面的人都可以 ...

  5. bzoj 1589: [Usaco2008 Dec]Trick or Treat on the Farm 采集糖果【tarjan+记忆化搜索】

    对这个奇形怪状的图tarjan,然后重新连边把图变成DAG,然后记忆化搜索即可 #include<iostream> #include<cstdio> using namesp ...

  6. 动态规划——I 记忆化搜索

    Description Michael喜欢滑雪百这并不奇怪, 因为滑雪的确很刺激.可是为了获得速度,滑的区域必须向下倾斜,而且当你滑到坡底,你不得不再次走上坡或者等待升降机来载你.Michael想知道 ...

  7. 【bzoj1415】[Noi2005]聪聪和可可 期望记忆化搜索

    题目描述 输入 数据的第1行为两个整数N和E,以空格分隔,分别表示森林中的景点数和连接相邻景点的路的条数. 第2行包含两个整数C和M,以空格分隔,分别表示初始时聪聪和可可所在的景点的编号. 接下来E行 ...

  8. POJ_1088_(dp)(记忆化搜索)

    滑雪 Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 95792   Accepted: 36322 Description ...

  9. NYOJ16|嵌套矩形|DP|DAG模型|记忆化搜索

    矩形嵌套 时间限制:3000 ms  |  内存限制:65535 KB 难度:4   描述 有n个矩形,每个矩形可以用a,b来描述,表示长和宽.矩形X(a,b)可以嵌套在矩形Y(c,d)中当且仅当a& ...

随机推荐

  1. git常见错误及解决方案总结

    git常见错误及解决方案总结 使用git在本地创建一个项目的过程  $ makdir ~/hello-world                              //创建一个项目hello- ...

  2. Flutter实战视频-移动电商-19.首页_火爆专区界面布局编写

    19.首页_火爆专区界面布局编写 看一下图片的效果 一个标题栏,下面是多行两列.里面可以用column布局,外面用Warp流式布局 有得小伙伴说这里可以用网格布局,网格布局的话还是有一定的效率问题.这 ...

  3. Eclipse+Maven+TestNg+ReportNg 生成测试报告

    http://blog.csdn.net/a542551042/article/details/46729585

  4. ASP.NET Response.Cookies

    //设置cookie Response.Cookies["loginPage"].Value = "login.aspx"; //命名并给值 Response. ...

  5. [WIP]C语言 realloc的坑

    创建: 2019/01/07 题外话,不知不觉又一年过去了,2019也要好好努力. 回到主题,在用动态循环数组实现queue的时候, 由于realloc的原因出现了一些莫名其妙的错误. 先开个题,晚点 ...

  6. HDU2087【KMP-next】

    思路: 利用next[]的转化. //#include <bits/stdc++.h> #include<cstdio> #include<string.h> #i ...

  7. ZOJ3175【公式化函数的思想】

    题意:  给出f(n,m)(m<n)的定义:大于m并且小于n的能整除m的数的个数. F(n)为m从1至n的f(n,m)的和. 给出n,求F(n). 思路: 就是计算n/1 +  n/2 + n/ ...

  8. CodeForces Canada Cup 2016【A,B,C,D】

    CodeForces 725A: 思路就是如果"最左"不是'>'这个了,那么这个右边的一定不可能到达左边了: 同理最右: CodeForces 725B: 有两个空姐,一个从 ...

  9. NSString 是否存在空格

    NSString *_string = [NSString stringWithFormat:@"123 456"]; NSRange _range = [_string rang ...

  10. TYVJ1432 楼兰图腾

    Description 平面上有 N(N≤[10]^5 ) 个点,每个点的横.纵坐标的范围都是 1~N,任意两个点的横.纵坐标都不相同.若三个点 (x_1,y_1),(x_2,y_2),(x_3,y_ ...