您的位置:首页 > 其它

UVa 12563 (01背包) Jin Ge Jin Qu hao

2014-09-29 01:19 351 查看
如此水的01背包,居然让我WA了七次。

开始理解错题意了,弄反了主次关系。总曲目最多是大前提,其次才是歌曲总时间最长。

题意:

在KTV房间里还剩t秒的时间,可以从n首喜爱的歌里面选出若干首(每首歌只能唱一次且如果唱就必须唱完),然后剩下至少1秒的时间来唱那首长678秒的歌曲。

总曲目最多的前提下,尽量使歌曲总时间最长。

分析:

所给时间为t,在t-1秒内进行01背包,num[i]来记录剩余时间为 i 时能长的最多曲目,如果曲目相同还要记录最长时间。

//#define LOCAL
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;

const int maxn = 10000;
int a[55], dp[maxn], num[maxn];

int main(void)
{
#ifdef LOCAL
freopen("12563in.txt", "r", stdin);
#endif

int T;
scanf("%d", &T);
for(int kase = 1; kase <= T; ++kase)
{
int n, t;
scanf("%d%d", &n, &t);
t--;
for(int i = 0; i < n; ++i)
{
scanf("%d", &a[i]);
if(a[i] > 180)    a[i] = 180;
}
memset(dp, 0, sizeof(dp));
memset(num, 0, sizeof(num));
for(int i = 0; i < n; ++i)
for(int j = t; j >= a[i]; --j)
{
if(num[j] < num[j-a[i]] + 1)
{
num[j] = num[j-a[i]] + 1;
dp[j] = dp[j-a[i]] + a[i];
}
else if(num[j] == num[j-a[i]] + 1)
{
dp[j] = max(dp[j], dp[j-a[i]] + a[i]);
}
}
printf("Case %d: %d %d\n", kase, num[t]+1, dp[t]+678);
}

return 0;
}


代码君
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: