百度之星资格赛 1003 度度熊与邪恶大魔王(二维dp)

分析
挺好的一道题
dp[i][j]表示打败i颗血j防御力的怪兽需要的最少宝石数
然后就好了,复杂度\(O(n+m*1000*10)\)

#include <bits/stdc++.h>
using namespace std;

#define ll long long
#define F(i,a,b) for(int i=a;i<=b;++i)
#define R(i,a,b) for(int i=a;i<b;++i)
#define mem(a,b) memset(a,b,sizeof(a))

int n,m;
int a[100100],b[100100],c[1010],d[1010];
ll f[1010][22];
const ll inf = 1e9;
void init()
{
    F(i,0,1000)F(j,0,10) f[i][j]=1e9;
    F(k,1,m)
    {
        if(d[k]==0) continue;
        for(int j=0;j<d[k]&&j<=10;++j)
        {
            int x=d[k]-j;
            for(int i=1;i<=x;++i) f[i][j]=min(f[i][j],(ll)c[k]);
            for(int i=x+1;i<=1000;++i) f[i][j]=min(f[i][j],f[i-x][j]+c[k]);
        }
    }
}

int main()
{
    while(scanf("%d %d",&n,&m)!=EOF)
    {
        F(i,1,n) scanf("%d %d",a+i,b+i);
        F(i,1,m) scanf("%d %d",c+i,d+i);
        init();
        ll ans=0;
        F(i,1,n)
        {
            if(f[a[i]][b[i]]==inf) { ans=-1;break; }
            ans+=f[a[i]][b[i]];
        }
        printf("%I64d\n",ans );
    }
    return 0;
}
posted @ 2017-08-06 21:44  遗风忘语  阅读(163)  评论(0编辑  收藏  举报