hdu3466

    这一题咋一看没法下手,但其实是简单01背包的变种。没有思路的时候可以这么想想,可能会有思路。首先我们能判断出这是一个01背包问题,其次我们想如何把问题转为为我们最简单的模型。这时候我们要充分考虑我们最初的模型。

for(i=0;i<n;i++)

for(j=m;j>=w[i];j--)

dp[j]=max(dp[j-w[i]]+v[i],dp[j]);

这是最初的模型,第二个for循环是从大到小,是为了这一层用到的是上一层的数据。这里还需要注意,是充分用到上一层的数据。问题肯定是在最初的模型上进行变种,但性质不会变,这点需要注意。

这里我们再看这个题目,有p和q,这里就有q和p的差值,差值肯定是有意义的我们需要往这上面去想想。一个容量的价值会多次计算,但只有后面需要用到的容量前面都有才会有更好的效果。第一层有q1-p1个数据是更新不了的,第二层有q2-p2个数据是更新不了的,这里只有q2-p2>q1-p1才符合上述要求。

#include <iostream>
#include<algorithm>
#include<stdio.h>
#include<cstring>
using namespace std;
const int MAX=510;
typedef struct
{
   int p,q,v,d;
}Node;
Node no[MAX];
bool cmp(const Node&a,const Node &b)
{
    return a.d<b.d;
}
int N,M,dp[5010];
int main()
{
    while(~scanf("%d%d",&N,&M))
    {
        memset(dp,0,sizeof(dp));
        for( int i=0;i<N;i++)
        {
            scanf("%d%d%d",&no[i].p,&no[i].q,&no[i].v);
            no[i].d=no[i].q-no[i].p;
        }
        sort(no,no+N,cmp);
        for( int i=0;i<N;i++)
            for( int j=M;j>=no[i].q;j--)
            dp[j]=max(dp[j],dp[j-no[i].p]+no[i].v);
        printf("%d\n",dp[M]);
    }
    return 0;
}


评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值