01背包***hihocoder

题目来自hihocoder

http://hihocoder.com/problemset/problem/1038

描述

且说上一周的故事里,小Hi和小Ho费劲心思终于拿到了茫茫多的奖券!而现在,终于到了小Ho领取奖励的时刻了!

小Ho现在手上有M张奖券,而奖品区有N件奖品,分别标号为1到N,其中第i件奖品需要need(i)张奖券进行兑换,同时也只能兑换一次,为了使得辛苦得到的奖券不白白浪费,小Ho给每件奖品都评了分,其中第i件奖品的评分值为value(i),表示他对这件奖品的喜好值。现在他想知道,凭借他手上的这些奖券,可以换到哪些奖品,使得这些奖品的喜好值之和能够最大。

提示一:合理抽象问题、定义状态是动态规划最关键的一步

提示二:说过了减少时间消耗,我们再来看看如何减少空间消耗

输入

每个测试点(输入文件)有且仅有一组测试数据。

每组测试数据的第一行为两个正整数N和M,表示奖品的个数,以及小Ho手中的奖券数。

接下来的n行描述每一行描述一个奖品,其中第i行为两个整数need(i)和value(i),意义如前文所述。

测试数据保证

对于100%的数据,N的值不超过500,M的值不超过10^5

对于100%的数据,need(i)不超过2*10^5, value(i)不超过10^3

输出

对于每组测试数据,输出一个整数Ans,表示小Ho可以获得的总喜好值。

样例输入
5 1000
144 990
487 436
210 673
567 58
1056 897
样例输出
2099
#include<cstdio>
using namespace std;
int main()
{
	int n,m;
	scanf("%d%d",&n,&m);
	int *need=new int[n];
	int* value=new int[n];
	for(int i=0;i<n;++i)
	   scanf("%d%d",need+i,value+i);
	int * f=new int[m]();
	for(int i=0;i<n;++i)
		for(int j=m;j>=need[i];--j)
			if(f[j]<f[j-need[i]]+value[i])
				f[j]=f[j-need[i]]+value[i];
	printf("%d\n",f[m-1]);
}
时间: 2024-10-29 06:09:59

01背包***hihocoder的相关文章

hihoCoder #1038 : 01背包(板子题)

#1038 : 01背包 时间限制:20000ms 单点时限:1000ms 内存限制:256MB 描述 且说上一周的故事里,小Hi和小Ho费劲心思终于拿到了茫茫多的奖券!而现在,终于到了小Ho领取奖励的时刻了! 小Ho现在手上有M张奖券,而奖品区有N件奖品,分别标号为1到N,其中第i件奖品需要need(i)张奖券进行兑换,同时也只能兑换一次,为了使得辛苦得到的奖券不白白浪费,小Ho给每件奖品都评了分,其中第i件奖品的评分值为value(i),表示他对这件奖品的喜好值.现在他想知道,凭借他手上的这

hihoCoder week6 01背包

01背包 题目链接 https://hihocoder.com/contest/hiho6/problem/1 #include <bits/stdc++.h> using namespace std; const int N = 500 + 10; int need[N], value[N]; int dp[100000+10]; int main () { int n,V; scanf("%d %d", &n, &V); for(int i=1;i<

hihoCoder - 1038 - 01背包 (经典动态规划问题!!)

#1038 : 01背包 时间限制:20000ms 单点时限:1000ms 内存限制:256MB 描述 且说上一周的故事里,小Hi和小Ho费劲心思终于拿到了茫茫多的奖券!而现在,终于到了小Ho领取奖励的时刻了! 小Ho现在手上有M张奖券,而奖品区有N件奖品,分别标号为1到N,其中第i件奖品需要need(i)张奖券进行兑换,同时也只能兑换一次,为了使得辛苦得到的奖券不白白浪费,小Ho给每件奖品都评了分,其中第i件奖品的评分值为value(i),表示他对这件奖品的喜好值.现在他想知道,凭借他手上的这

hihocoder(1038,1043) 01背包与完全背包

动态规划是一直感觉比较模糊的东西,虽然大致上知道是什么一回事,但是离灵活应用还差得远,但貌似比赛中动态规划的题出的特别多,这两个经典问题其实只能算是一个学习动态规划很好的模型.不过万事开头难,关键还是得静下心来多练习. 01背包的状态转移式:f(i, j) = max{f(i-1, j), f(i-1, j-need[i])+value[i]} 直接按照上述的状态转移式申请二维数组进行运算,伪代码如下: fori : 1..N f(0,j) = 0 for i : 1..N for j : 0.

hihoCoder#1055 : 刷油漆 (树形DP+01背包)

题目大意:给一棵带点权的树,现在要从根节点开始选出m个连通的节点,使总权值最大. 题目分析:定义状态dp(u,m)表示在以u为根的子树从根节点开始选出m个点连通的最大总权值,则dp(u,m)=max(dp(u,m),dp(u,m-k)+dp(son,k)),其中0<=k<m.这是01背包,k应该从大往小枚举. 代码如下: # include<iostream> # include<cstdio> # include<cmath> # include<v

hihoCoder1055.刷油漆——树形Dp+01背包

http://hihocoder.com/problemset/problem/1055 一棵有根树,包含根节点1,选择M个连续的节点,使得权值最大 dp[u][j] 表示以i为根的子树中,选择包含根节点的j个连续节点所能获得的最大权值 枚举子节点选择的个数,儿子节点选择的个数,当做01背包 #include <iostream> #include <cstring> #include <cstdio> #include <vector> #include

UVA 562 Dividing coins --01背包的变形

01背包的变形. 先算出硬币面值的总和,然后此题变成求背包容量为V=sum/2时,能装的最多的硬币,然后将剩余的面值和它相减取一个绝对值就是最小的差值. 代码: #include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> using namespace std; #define N 50007 int c[102],d

17-又见01背包

/*                                        又见01背包时间限制:1000 ms  |  内存限制:65535 KB难度:3 描述        有n个重量和价值分别为wi 和 vi 的 物品,从这些物品中选择总重量不超过 W     的物品,求所有挑选方案中物品价值总和的最大值.    1 <= n <=100    1 <= wi <= 10^7    1 <= vi <= 100    1 <= W <= 10^

HDU - 2602 Bone Collector(01背包讲解)

题意:01背包:有N件物品和一个容量为V的背包.每种物品均只有一件.第i件物品的费用是volume[i],价值是value[i],求解将哪些物品装入背包可使价值总和最大. 分析: 1.构造二维数组:dp[i][j]---前i件物品放入一个容量为j的背包可以获得的最大价值. dp[i][j] = max(dp[i - 1][j], dp[i - 1][j - volume[i]] + value[i]);---(a) (1)dp[i - 1][j]---不放第i件物品,因此前i件物品放入一个容量为