zoukankan      html  css  js  c++  java
  • 【每日一题】22.美味菜肴 ( 01背包变种问题 )

    补题链接:Here

    首先必须理解到这是一道背包问题,但直接写背包肯定是错的,因为这里多了一个时间的限制:物品价值随时间变化

    同样是背包但是先进背包和后进背包有区别
    因此需要考虑贪心策略下背包

    对于两个物体 (A,B) 先取 (A) 物体比先取(B) 物体优

    数学表达

    [a_i- b_i * c_i + a_j - b_j * (c_i + c_j) > a_j - b_j * c_j + a_i - b_i*(c_i+c_j) \ 化简: b_j* c_i < b_i * c_j ]

    排序后进行背包就行了
    注意题目要求必须至少做一道菜, 这里有个人尽皆知的小技巧:把 dp 数组初始化为无穷小,且 (dp_0 = 0) 这样保证至少取一个

    using ll    = long long;
    const int N = 1 << 20;
    ll dp[N];
    ll a[N], b[N], c[N], j[N], k[N];
    bool cmp(int x, int y) { return b[j[x]] * c[y] > b[j[y]] * c[x]; }
    void solve() {
        int n, m, t;
        cin >> n >> m >> t;
        for (int i = 1; i <= n; ++i) cin >> b[i];
        for (int i = 1; i <= m; ++i) cin >> j[i] >> a[i] >> c[i], k[i] = i;
        sort(k + 1, k + 1 + m, cmp);
        memset(dp, -0x3f, sizeof(dp));
        for (int i = 1; i <= m; ++i) {
            int v = k[i];
            for (int l = t; l >= c[v]; --l)
                dp[l] = max(dp[l], dp[l - c[v]] + a[v] - l * b[j[v]]);
        }
        ll ans = -1e18;
        for (int i = 1; i <= t; ++i) ans = max(ans, dp[i]);
        cout << ans << "
    ";
    }
    

    The desire of his soul is the prophecy of his fate
    你灵魂的欲望,是你命运的先知。

  • 相关阅读:
    要想成功,要先学会放弃:30条经典做人的哲学
    薛家德(帮别人名字作诗)
    激励一生的七个经典故事
    出色管理者的时间管理
    王华(帮别人名字作诗)
    申维维(帮别人名字作诗)
    王磊(帮别人名字作诗)
    秋凉
    牛佳(帮别人名字作诗)
    共度良宵
  • 原文地址:https://www.cnblogs.com/RioTian/p/14752378.html
Copyright © 2011-2022 走看看