UVA 10465 Homer Simpson(全然背包: 二维目标条件)
UVA 10465 Homer Simpson(全然背包: 二维目标条件)
http://uva.onlinejudge.org/index.php?
option=com_onlinejudge&Itemid=8&page=show_problem&problem=1406
题意:
有两种汉堡包(汉堡数量无限多),第一种吃一个须要花n分钟,另外一种吃一个须要花m分钟. 如今你有t分钟的时间, 问你最少浪费几分钟不能吃汉堡(你每次要么完整的吃完一个汉堡,要么不吃). 当吃汉堡花费的时间达到最大时, 问你最多能吃几个汉堡?
分析:
本题的限制条件是: 总时间<=t分钟.
本题的目标条件是: 总时间尽量大, 假设时间同样的情况下汉堡数目越多越好.
二维(甚至多维)目标条件有两种方法能够做.
第一种方法是:先用全然背包求出最大时间tmax, 然后再用一次全然背包求出吃汉堡的时间正好等于最大时间tmax下, 最多能吃几个汉堡.
首先用全然背包求出最大时间tmax. 令dp[i][j]==x表示当决策完前i个汉堡后, 总时间不超过j分钟时最多能花x分钟. 那么有以下递推公式:
dp[i][j] = max( dp[i-1][j] , dp[i][j-time[i]]+time[i] )
前者表示一个i 汉堡都不选,后者表示至少选1个i汉堡.
初始化为dp全0. 终于tmax=dp[n][t].
然后我们求在花费时间正好tmax的情况下的最大汉堡数. 令dp[i][j]==x 表示决策全然i个物品后, 时间正好为j分钟时的最大汉堡数目为x个. 那么有以下递推公式:
dp[i][j] = max( dp[i-1][j] , dp[i][j-time[i]]+1)
前者表示一个i 汉堡都不选,后者表示至少选1个i汉堡.
初始化为dp全-1.且dp[0][0]=0.
终于最大汉堡数=dp[n][tmax].
另外一种方法是:
UVA12563题目一样的思想:
http://blog.csdn.net/u013480600/article/details/40376143
一般我们做的背包问题都是问你<=t的时间内, 怎样选择哪些汉堡(在不超过总时间的前提下)能使得吃的时间最长或 吃的汉堡最多. 可是本题须要同一时候考虑两个最优条件, 那么该怎么做呢?
我们令dp[i][j]==x 表示当决策全然前i个物品后(选或不选), 吃汉堡花的时间<=j时, 所得到的最优状态为x. (这里的x就不是平时我们所说的最长时间或最多歌曲数目了)
怎么理解最优状态为x这个事实呢? 如果有两种选择前i个汉堡的方法能使得决策完前i个物品且总时长<=j时的状态分别为x1
和x2.
那么假设x1状态的吃汉堡时间> x2状态的吃汉堡时间, 那么明显x1状态更优. 所以dp[i][j]应==x1.
假设x1状态的吃汉堡时间与x2的相等, 可是x2状态的吃汉堡数目 > x1状态的吃汉堡数目, 那么此时x2状态更优. 所以dp[i][j]应==x2.
经过上面的分析,我们能够用一个(具有吃汉堡时间和吃汉堡数目双属性的)结构体来表示一个状态. 且能够得到以下状态转移公式:
dp[i][j] = 最优(dp[i-1][j] , 在dp[i-1][j-time[i]]的基础上选择第i个汉堡后得到的新状态tmp
)
全部dp初始化为0就可以. 终于我们所求为dp[n][t]
程序实现用的滚动数组,所以dp仅仅有[j]这一维.
AC代码1:用方法1两次DP做的
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=10000+5; int n,m,t;//相应题意的含义
int time[5];//吃第i种汉堡所花时间
int dp[maxn]; int main()
{
while(scanf("%d%d%d",&time[1],&time[2],&t)==3)
{
//递推最大时间
memset(dp,0,sizeof(dp));
for(int i=1;i<=2;i++)
{
for(int j=time[i];j<=t;j++)
dp[j] = max(dp[j], dp[j-time[i]]+time[i]);
}
int tmax=dp[t]; //递推最大汉堡数目
memset(dp,-1,sizeof(dp));
dp[0]=0;
for(int i=1;i<=2;i++)
{
for(int j=time[i];j<=tmax;j++)if(dp[j-time[i]]!=-1)
dp[j] = max(dp[j], dp[j-time[i]]+1);
} //输出结果
printf("%d",dp[tmax]);
if(t>tmax) printf(" %d",t-tmax);
printf("\n");
}
return 0;
}
AC代码2:用方法2一次DP做的
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=10000+5; int n,m,t; //相应题意的含义
int time[5];//吃第i种汉堡所花时间
struct Node //每一个状态
{
int time;//吃汉堡时间
int num; //吃汉堡数目
bool operator<(const Node &rhs)const
{
return time<rhs.time || (time==rhs.time && num<rhs.num);
}
}dp[maxn]; int main()
{
while(scanf("%d%d%d",&time[1],&time[2],&t)==3)
{
//初始化
memset(dp,0,sizeof(dp)); //递推
for(int i=1;i<=2;i++)
{
for(int j=time[i];j<=t;j++)
{
Node tmp=dp[j-time[i]];
tmp.time += time[i];
tmp.num++;
if(dp[j]<tmp) dp[j]=tmp;
}
} //输出结果
printf("%d",dp[t].num);
if(dp[t].time<t) printf(" %d",t-dp[t].time);
printf("\n");
}
return 0;
}
UVA 10465 Homer Simpson(全然背包: 二维目标条件)的更多相关文章
- UVA 10306 e-Coins(全然背包: 二维限制条件)
UVA 10306 e-Coins(全然背包: 二维限制条件) option=com_onlinejudge&Itemid=8&page=show_problem&proble ...
- UVa 10465 Homer Simpson (枚举)
10465 - Homer Simpson Time limit: 3.000 seconds http://uva.onlinejudge.org/index.php?option=com_onli ...
- UVa 10465 Homer Simpson(DP 全然背包)
题意 霍默辛普森吃汉堡 有两种汉堡 一中吃一个须要m分钟 还有一种吃一个须要n分钟 他共同拥有t分钟时间 要我们输出他在尽量用掉全部时间的前提下最多能吃多少个汉堡 假设时间无法用 ...
- UVA 10465 Homer Simpson(dp + 完全背包)
Problem C: Homer Simpson Time Limit: 3 seconds Memory Limit: 32 MB Homer Simpson, a very smart guy, ...
- HDU 2159 FATE(全然背包+二维费用背包)
FATE Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submi ...
- 10465 - Homer Simpson 贪心
Homer Simpson Time Limit: 3 seconds Memory Limit: 32 MB Home ...
- HDU 2159 FATE(二维全然背包)
中文题目就不用解释了 就是裸的二维全然背包 d[i][j]表示消耗i忍耐杀j个怪最多可获得的经验 然后就用全然背包来做了 二维背包背包只是是多了一重循环 <span style=&quo ...
- HDU2159 二维完全背包
FATE Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
- DP:Cow Exhibition(POJ 2184)(二维问题转01背包)
牛的展览会 题目大意:Bessie要选一些牛参加展览,这些牛有两个属性,funness和smartness,现在要你求出怎么选,可以使所有牛的smartness和funness的最大,并且这两 ...
随机推荐
- 使用Docker运行Microsoft SQL Server 2017
最近每天都在空闲时间努力编写Apworks框架的案例代码WeText.在文本发布和处理微服务中,我打算使用微软的SQL Server for Linux来做演示,于是也就在自己的docker-comp ...
- Python 解LeetCode:680. Valid Palindrome II
题目:给定一个字符串,在最多删除一个字符的情况下,判断这个字符串是不是回文字符串. 思路:回文字符串,第一想到的就是使用两个指针,前后各一个,当遇到前后字符不一致的时候,有两种情况,删除前面字符或者删 ...
- 关于SQLServer数据库中字段值为NULL,取出来该字段放在DataTable中,判断datatable中该字段值是否为NULL的三种方法
1. DataTable dt; //假设字段为name, dt已经保存了数据dt.rows[0]["name"] == ...
- 来手撸一个小小小小小"3D引擎"
开始的唠叨 说是3D引擎确实有点过于博眼球了,其实就是实现了一个透视投影,当然也不是那么简单的. 此篇文章是纯粹给小白看的 高手请勿喷 .也称之为小向带你图形学入门基础 . 哇哈哈哈哈 一说到做一个3 ...
- cocos2dx3.0导出自定义类到lua的方法详细步骤
我写了一个用3.0的工具导出类到lua,自动生成代码的方法. 以前要导出c++类到lua,就得手动维护pkg文件,那简直就是噩梦,3.0以后就会感觉生活很轻松了. 下面我就在说下具体做法.1.安装必要 ...
- Linux上安装和卸载mysql数据库 (一)
一.前言 第一次写博客,很激动同时有点畏惧,激动是我可以将我的经验进行分享,畏惧是我怕我写的东西,大家借鉴的时候,有些步骤不能成功.不过,我还是很有信息的,我分享的经验都是我搭建成功以后才分享出来.这 ...
- 条件随机场 Conditional Random Fields
简介 假设你有冠西哥一天生活中的照片(这些照片是按时间排好序的),然后你很无聊的想给每张照片打标签(Tag),比如这张是冠西哥在吃饭,那张是冠西哥在睡觉,那么你该怎么做呢? 一种方法是不管这些照片的序 ...
- .net 通用面试题
1. private. protected. public. internal 修饰符的访问权限. private : 私有成员, 在类的内部才可以访问 public : 公共成员,完全公开,没有访问 ...
- JAVAFX-5事件总结
事件监听 在RIA 或者说 桌面客户端gui android 开发中,事件的机制是必须的要学习了解的, 分类处理类型 在Java GUI 和swing中,事件通常通过实现listener的接口函数,并 ...
- TCP/IP协议栈 ARP和RARP协议
上几章中我们提到以太网协议中,在以太网首部中一个帧类型的字段,它可以表示为IP ARP RARP协议. 这里说一下ARP 和RARP协议. 首先看ARP协议: 要想网络中的数据包准确到达某个主机,最后 ...