poj2063 Investment(完全背包)


http://poj.org/problem?id=2063

题意:Jone想做一笔投资。现在他有一笔初始资金,准备做几年的投资。他想买债券,债券的归还期为一年,也就是说每到一年他得回收本金与利息,再次购买新的债券。债券有n种,每种的价格和利息(每年)都列举出来。求最大收益。


ps:好难懂的题意,不过很贴近于生活。


思路:由于想买的债券每种都是无限数量,所以是完全背包求不超过每年初始资金的最大利息。由于债券可以被1000整除,所以背包中原始资金的容量也应该除以1000。这里dp的最大范围比较难算,1 000 000/1000=1000后每年利息不超过10%,也就是说40年后至少也有100*40=4000的利息,不过以防万一,还是尽量往大开好了。这里RE了一次。另外,这题背包是未装满,初始dp为0。还有,用二维的话会爆内存,所以一般情况还是能用一维就用一维吧。


#include 
#include 
#include 
#include 
#include 

using namespace std;

typedef long long LL;

const int N = 46005;
const int INF = 0x3f3f3f3f;

int dp[N];

int main()
{
   // freopen("in.txt", "r", stdin);
    int t, V, n, time;
    int cost[N], weight[N];
    scanf("%d", &t);
    while(t--)
    {
        scanf("%d%d", &V, &time);
        scanf("%d", &n);//物品数量
        for(int i = 1; i <= n; i++)
        {
            scanf("%d%d", &cost[i], &weight[i]);
            cost[i]/=1000;
        }
        int V0 = V;
        int inte = 0;//利息
        for(int k = 1; k <= time; k++)
        {
            memset(dp, 0, sizeof(dp));//未装满
            V += inte;
            V0 = V/1000;
            for(int i = 1; i <= n; i++)
                for(int j = cost[i]; j <= V0; j++)
                {
                    dp[j] = max(dp[j], dp[j-cost[i]]+weight[i]);
                }
            inte = dp[V0];
        }
        printf("%d\n", V+inte);
    }
    return 0;
}


想了想还是把爆内存的二维贴上来吧。

#include 
#include 
#include 
#include 
#include 

using namespace std;

typedef long long LL;

const int N = 4600;
const int INF = 0x3f3f3f3f;

int dp[N][N];

int main()
{
 //   freopen("in.txt", "r", stdin);
    int t, V, n, time;
    int cost[N], weight[N];
    scanf("%d", &t);
    while(t--)
    {
        scanf("%d%d", &V, &time);
        scanf("%d", &n);//物品数量
        for(int i = 1; i <= n; i++)
        {
            scanf("%d%d", &cost[i], &weight[i]);
            cost[i]/=1000;
        }
        int V0 = V;
        int inte = 0;//利息
        for(int k = 1; k <= time; k++)
        {
            memset(dp, 0, sizeof(dp));//未装满
            V += inte;
            V0 = V/1000;
            for(int i = 1; i <= n; i++)
                for(int j = 0; j <= V0; j++)
                {
                    if(j < cost[i]) dp[i][j] = dp[i-1][j];
                    else dp[i][j] = max(dp[i-1][j], dp[i][j-cost[i]]+weight[i]);
                }
            inte = dp[n][V0];
            printf("[%d]\n", inte);
        }
        printf("%d\n", V+inte);
    }
    return 0;
}



你可能感兴趣的:(poj,动态规划-背包)