6 条题解
-
1
假设 Sam 选择了一组物品集合 ,其总重量为 ,总体积为 。
根据题意,需要存在一个自然数 ,使得选择的物品满足:
因此,只需能够找到一个非负整数 满足 。此类非负整数 存在的充要条件为:
问题化简为:选择若干物品,在满足总重量 且 总重量与总体积之和 的前提下,求解能获得的最大价值和。
这是一个标准的二维 01 背包问题:
- 第一维度限制:总重量 (最大为 )。
- 第二维度限制:总重量 + 总体积 (最大为 )。
定义
f[j][k]表示总重量不超过 且(总重量+总体积)不超过 时的最大价值。对于每个物品 (重量 ,体积 ,价值 ),令 :
$$f[j][k] = \max(f[j][k], f[j - h_i][k - sum_i] + w_i)$$采用倒序遍历实现滚动数组,时间复杂度为 ,运算量约为 。
-
1
以下大家的思路已经十分清晰了
再此补一份代码:#include<bits/stdc++.h> #define ll long long//不开long long见祖宗 using namespace std; const int N=1e3+5;//605 1e3+5省事 int n,H,V; ll dp[N][N]; int main(){ freopen("dp.in","r",stdin); freopen("dp.out","w",stdout); cin>>n>>H>>V; for(int i=1;i<=n;i++){ int h,v;ll w;cin>>h>>v>>w; for(int j=H;j>=h;j--){//∑h_i<=j H-x<=H for(int k=V+H;k>=v;k--){//∑v_i<=k V+x<=V+H dp[j][k]=max(dp[j][k],dp[j-h][k-v]+w); //不选i,dp[j][k]在滚动数组中为以前的答案 //选i,在以前质量没有h,体积没有v的时候的答案加上i的价值 } } } ll ans=0; for(int i=0;i<=H;i++)//枚举每个x ans=max(ans,dp[H-i][V+i]); cout<<ans<<'\n'; }
- 1
信息
- ID
- 2736
- 时间
- 1000ms
- 内存
- 64MiB
- 难度
- 3
- 标签
- (无)
- 递交数
- 53
- 已通过
- 13
- 上传者