AcWing 4. 多重背包问题 I

题目链接:点击这里
在这里插入图片描述
在这里插入图片描述

多重背包问题描述:有 N N 种物品和一个容量为 V V 的背包。第 i i 种物品最多有 M i M_i 件可用,每件耗费的空间是 C i C_i ,价值是 W i W_i 。求解将哪些物品装入背包可使这些物品的耗费的空间总和不超过背包容量,且价值总和最大。

这题目和完全背包问题很类似。基本的方程只需将完全背包问题的方程略微一改即可。

因为对于第 i i 种物品有 M i + 1 M_i + 1 种策略:取 0 0 件,取 1 1 件……取 M i M_i 件。

F [ i , v ] F[i, v] 表示前 i i 种物品恰放入一个容量为 v v 的背包的最大价值,则有状态转移方程:
F [ i v ] = m a x { F [ i 1 , v k C i ] + k W i 0 k M i } F[i, v] = max\left\{F[i − 1, v − k ∗ C_i] + k ∗ W_i | 0 ≤ k ≤ M_i\right\}

复杂度是 O ( N V Σ M i ) O(NV ΣM_i)

#include<iostream>
#include<cstdio>
#include<algorithm>

using namespace std;

const int maxn = 110;

int v[maxn], w[maxn], s[maxn];		//v物品体积,w物品价值,s物品数量 

int dp[maxn];

int main()
{
    int N, V;
    scanf("%d%d", &N, &V);
    
    for(int i = 1; i <= N; ++i)
        scanf("%d%d%d", &v[i], &w[i], &s[i]);
    
    for(int i = 1; i <= N; ++i)
    {
        for(int j = V; j >= v[i]; --j)
        {
        	for(int k = 0; k <= s[i] && k*v[i] <= j; ++k)
        	{
        		dp[j] = max(dp[j], dp[j-k*v[i]]+k*w[i]);
			}
        }
    }
    
    printf("%d", dp[V]);
    
    return 0;
}
发布了748 篇原创文章 · 获赞 113 · 访问量 13万+

猜你喜欢

转载自blog.csdn.net/qq_42815188/article/details/104363861