原题链接:​​http://acm.fzu.edu.cn/problem.php?pid=2214​

这题不能按照传统01背包来做,它的容量太大,数组会爆掉。注意到物品个数较小,而且价值和最大只有5000,所以可以逆向思维,求得对应价
值下最小的重量,即dp[i]表示总价值为i的最小重量是多少,则dp[j] = min(dp[j] , dp[j-val[i]]+vol[i]);最后从sum(物品总价值开始判
断)开始,找到第一个小于等于b(容量)的v即可。。。

#include<iostream>
#include<stdio.h>
#include<algorithm>
using namespace std;
#define INF 1000000005
int t;
int n, b;
int sum;
int w[505];
int v[505];
int dp[5005];

int main()
{

scanf("%d", &t);
while (t--)
{
sum = 0;
scanf("%d%d", &n, &b);
for (int i = 1; i <= n; i++)
{
scanf("%d%d", &w[i], &v[i]);
sum += v[i];
}

dp[0] = 0;
for (int i = 1; i <= sum; i++)
dp[i] = INF;

for (int i = 1; i <= n; i++)
{
for (int j = sum; j >= v[i]; j--)
{
if (dp[j - v[i]] + w[i] <= b) //大于b没有意义
dp[j] = min(dp[j], dp[j - v[i]] + w[i]);
}
}

for (int i = sum; i >= 0; i--)
{
if (dp[i] <= b)
{
printf("%d\n", i);
break;
}
}
}
return 0;
}