FZU-2214 Knapsack problem(DP使用)

Problem 2214 Knapsack problem

Accept: 863    Submit: 3347
Time Limit: 3000 mSec    Memory Limit : 32768 KB

 Problem Description

Given a set of n items, each with a weight w[i] and a value v[i], determine a way to choose the items into a knapsack so that the total weight is less than or equal to a given limit B and the total value is as large as possible. Find the maximum total value. (Note that each item can be only chosen once).

 Input

The first line contains the integer T indicating to the number of test cases.

For each test case, the first line contains the integers n and B.

Following n lines provide the information of each item.

The i-th line contains the weight w[i] and the value v[i] of the i-th item respectively.

1 <= number of test cases <= 100

1 <= n <= 500

1 <= B, w[i] <= 1000000000

1 <= v[1]+v[2]+...+v[n] <= 5000

All the inputs are integers.

 Output

For each test case, output the maximum value.

 Sample Input

1 5 15 12 4 2 2 1 1 4 10 1 2

 Sample Output

15

 Source

第六届福建省大学生程序设计竞赛-重现赛(感谢承办方华侨大学)

 

原题地址
#include<iostream>
#include<cstring>
#include<algorithm>
#define INF 0x3f3f3f3f
using namespace std;
int w[505];
int v[505];
long long dp[5005];
int n,m;

int main(){
        int t;
        std::ios::sync_with_stdio(false);
        cin>>t;
        while(t--){
                cin>>n>>m;
                int sum=0;
                for(int i=0;i<n;i++){
                        cin>>w[i]>>v[i];
                        sum+=w[i];
                }
                memset(dp,INF,sizeof(dp));
                dp[0]=0;
                for(int i=0;i<n;i++){
                        for(int j=5000;j>=0;j--){///价值
                                if(j>=v[i]){
                                        dp[j]=min(dp[j],dp[j-v[i]]+w[i]);
                                        dp[j]=dp[j]==0?(dp[j-v[i]]+w[i]):min(dp[j],dp[j-v[i]]+w[i]);
                                        ///存重量
                                }

                        }
                }
                int ans=0;
                for(int i=0;i<=5000;i++){
                      //  dp[i]=0x3f3f3f3f-dp[i];
               //         cout<<i<<" "<<dp[i]<<endl;
                        if(dp[i]<=m&&i>ans){
                                ans=i;
                        }
                }
                cout<<ans<<endl;
        }
}

  

 
题意:给你N个物品,每个物品都有自己的价值和需要的容量,M的容量,问你不超过M最大的价值,带上M太大数组存不下
 
思路:所以换个思路,把容量换价值转换成得到价值使得容量最小,这是数组只要5000 复杂度是O(n*5000)
代码:
 
posted @ 2018-05-06 01:59  luowentao  阅读(179)  评论(0编辑  收藏  举报