又見01背包
時間限制: 1000 ms | 記憶體限制: 65535 KB 難度: 3
- 描述
- 有n個重量和價值分别為wi 和 vi 的 物品,從這些物品中選擇總重量不超過 W 的物品,求所有挑選方案中物品價值總和的最大值。 1 <= n <=100 1 <= wi <= 10^7 1 <= vi <= 100 1 <= W <= 10^9
- 輸入
-
多組測試資料。
每組測試資料第一行輸入,n 和 W ,接下來有n行,每行輸入兩個數,代表第i個物品的wi 和 vi。
輸出 - 滿足題意的最大價值,每組測試資料占一行。 樣例輸入
-
4 5 2 3 1 2 3 4 2 2
樣例輸出 -
7
-
01背包,看資料用最基本的方法空間肯定不夠,此時就要轉換一下;
原來數組的角标表示的是空間,空間一定,求最大價值
可以把角标轉換成價值,價值一定,求最小空間,此時最大的空間即有最大價值
#include <iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#define mem(a,b) memset(a,b,sizeof(a))
using namespace std;
typedef long long ll;
ll f[10005],w[105],v[105];
int main()
{
ll n,m;
while(~scanf("%lld%lld",&n,&m))
{
ll t=0;
for(ll i=0;i<n;i++)
{
scanf("%lld%lld",&w[i],&v[i]);
t+=v[i];
}
mem(f,0x3f3f3f3f);
f[0]=0;
for(int i=0;i<n;i++)
{
for(int j=t;j>=v[i];j--)
{
f[j]=min(f[j-v[i]]+w[i],f[j]);
}
}
for(int i=t;i>=0;i--)
{
if(f[i]<=m)
{
printf("%lld\n",i);
break;
}
}
}
return 0;
}