1. 程式人生 > >2602  )和完全揹包(POJ

2602  )和完全揹包(POJ

POJ - 1384  完全揹包問題,體積要求有點區別,要求豬是100斤就只能是100斤(必須裝滿)

然後我想起來另一道題HDU - 2602 ,這是經典的01揹包裸題了,求給定最大體積下最大為多少價值(允許不裝滿)。

括號就是差別,當然,不是說01一定是允許不裝滿,完全揹包一定是必須裝滿。這種條件差別的解決涉及到另外一個問題,memset的初始化。

確定條件:dp方程肯定是沒問題的,要在上面進行修改。

問題:如何知道裝不滿?

答:立flag啊,flag倒了就說明沒裝滿。

問:咋立flag?

答:沒裝滿的標為false,裝滿的標為true。

實際操作中我們不需要再開一個數組,我們可以通過處理dp方程來解決,裝滿的體現一個數值,沒裝滿的位置體現為INF,根據dp的思想我們可以確定,dp[j] = min(dp[j-wei[i]]+val[i],dp[j]);如果min裡面倆位置都沒裝滿,肯定都>=INF,可以體現此時沒裝滿。

得出結論:其實和啥揹包沒關係,主要是初始化問題。

附上程式碼:

/*POJ - 1384*/

#include<iostream>
#include<cmath>
#include<cstdlib>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
int N,M;
#define INF 0x3f3f3f3f
const int maxn = 1003;
int dp[maxn*10];
int val[maxn],wei[maxn];
int main()
{
    ios::sync_with_stdio(false);
    int n,all_wei;
    cin>>n;
    while(n--)
    {
        memset(dp,INF,sizeof(dp));
        dp[0] = 0;
        int a,b;
        cin>>a>>b;
        all_wei = b-a;
        int t;
        cin>>t;
        for(int i=0;i<t;i++)
            cin>>val[i]>>wei[i];
        for(int i=0;i<t;i++)
        {
            for(int j=wei[i];j<=all_wei;j++)
            {
                dp[j] = min(dp[j-wei[i]]+val[i],dp[j]);
            }
        }
        if(all_wei < 0 || dp[all_wei] == INF)
            cout<<"This is impossible."<<endl;
        else cout<<"The minimum amount of money in the piggy-bank is "<<dp[all_wei]<<"."<<endl;
    }
    return 0;
}
/*HDU - 2602*/

#include <bits/stdc++.h>
#define INF 0x3f3f3f3f
using namespace std;
typedef long long ll ;
const int maxn = 1003;
int t;
int n,v;
int val[maxn];
int wei[maxn];
int dp[1003];
int main()
{
    //freopen("in.txt","r",stdin);
    ios::sync_with_stdio(false);
    int t;
    cin>>t;
    while(t--)
    {
        memset(dp,0,sizeof(dp));
        cin>>n>>v;
        for(int i=0;i<n;i++)
            cin>>val[i];
        for(int i=0;i<n;i++)
            cin>>wei[i];
        for(int i=0;i<n;i++)
        {
            for(int j = v;j>=wei[i];j--)
            {
                dp[j] = max(dp[j-wei[i]]+val[i],dp[j]);
            }
        }
        cout<<dp[v]<<endl;
    }
    return 0;
}