码迷,mamicode.com
首页 > 其他好文 > 详细

P1417 烹调方案(思维+01背包)

时间:2019-09-06 21:18:42      阅读:97      评论:0      收藏:0      [点我收藏+]

标签:tar   hid   选择   --   ios   display   问题   ons   完成   

(点击此处查看原题)

题意

有n种食材,每种食材有三个属性,ai,bi和ci,如果在t时刻完成第i样食材则得到ai-t*bi的美味指数,用第i件食材做饭要花去ci的时间。问在T时间内,什么样的烹调方案使得美味指数最大,输出最大的美味指数

解题思路

简单看来,这就是一个01背包问题,但是不同之处在于这里每个食材的价值会因为时间而改变,所以对于每个时间点,我们需要考虑此时先选择哪一种食材

记now为当前时间,食材1的属性:a1,b1,c1,食材2的属性:a2,b2,c2

1)先选择食材1的总价值:a1 - (now  + c1) * b1 + a2 - (now + c1 + c2 ) * b2;

2)先选择食材2的总价值:a2 - (now  + c2) * b2 + a1 - (now + c1 + c2 ) * b1

两者比较一下,发现当 c1 * b2 < c2 * b1 的时候,先选取食材1的价值更大,那么我们就将n种食材按照这样的方式排序,随后就是01背包处理了

代码区

技术图片
#include<iostream>
#include<cstdio>
#include<algorithm>
#define LOCAL = 1;
using namespace std;
typedef long long ll;
const int Max = 1e5 + 10;

struct Node
{
    ll a, b, c;
} node[55];

int v, n;
ll dp[Max];        //记录在第i时刻的最大价值

bool cmp(Node x, Node y)
{
    return x.c * y.b < y.c * x.b;
}

int main()
{
#ifdef LOCAL
    //    freopen("input.txt", "r", stdin);
    //    freopen("output.txt", "w", stdout);
#endif
    scanf("%d%d", &v, &n);
    for (int i = 1; i <= n; i++)
        scanf("%lld", &node[i].a);
    for (int i = 1; i <= n; i++)
        scanf("%lld", &node[i].b);
    for (int i = 1; i <= n; i++)
        scanf("%lld", &node[i].c);

    sort(node + 1, node + 1 + n,cmp);

    for (int i = 1; i <= n; i++)
    {
        for (int j = v; j >= node[i].c; j--)
        {
            dp[j] = max(dp[j], dp[j - node[i].c] + node[i].a - j * node[i].b);
        }
    }
    ll max_val = 0;
    for (int j = 1; j <= v; j++)
    {
        max_val = max(dp[j], max_val);
    }
    printf("%lld\n", max_val);
    return 0;
}
View Code

P1417 烹调方案(思维+01背包)

标签:tar   hid   选择   --   ios   display   问题   ons   完成   

原文地址:https://www.cnblogs.com/winter-bamboo/p/11478252.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!