2017百度之星-1003度度熊与邪恶大魔王

度度熊与邪恶大魔王

题意:中文题

思路:完全背包,以血量作为背包容量,以花费晶石做为价值,求花费晶石最小也就是求背包价值最小,注意,dp[i]表示的是血量为i的怪物恰好被杀死的最小花费,所以如果出现i更大,但是花费更小的,应该要更新答案,从后面遍历每次判断dp[i-1]和dp[i]的大小就可以了,题目中还有一个条件,防御值,当防御值大于攻击力的时候攻击无效,所以开一个二维即可,每次判断一下技能能否奏效,如果不能则不进入背包,最后dp式为 dp[t][j]=max(dp[t][j],dp[t][j-pi]+ki)

AC代码:怕查重 ,还是删了。。。

代码:

#include "iostream"
#include "string.h"
#include "stack"
#include "queue"
#include "string"
#include "vector"
#include "set"
#include "map"
#include "algorithm"
#include "stdio.h"
#include "math.h"
#pragma comment(linker, "/STACK:102400000,102400000")
#define ll long long
#define endl ("\n")
#define bug(x) cout<<x<<" "<<"UUUUU"<<endl;
#define mem(a,x) memset(a,x,sizeof(a))
#define mp(x,y) make_pair(x,y)
#define pb(x) push_back(x)
#define ft (frist)
#define sd (second)
#define lrt (rt<<1)
#define rrt (rt<<1|1)
using namespace std;
const long long INF = 1e18+1LL;
const int inf = 1e9+1e8;
const int N=1e5+100;
const ll mod=1e9+7;

ll dp[15][2500],n,m,a[N],b[N],ct[1005],vi[1005];
int main(){
    while(~scanf("%I64d %I64d",&n, &m)){
        for(int i=1; i<=n; ++i){
            scanf("%I64d %I64d",&a[i], &b[i]);
        }
        for(int i=1; i<=m; ++i){
            scanf("%I64d %I64d",&ct[i], &vi[i]);
        }
        for(int i=0; i<=10; ++i){
            for(int j=0; j<=2000; ++j){
                if(j==0) dp[i][j]=0;
                else dp[i][j]=inf;
            }
        }
        for(int t=0; t<=10; ++t){
            for(int i=1; i<=m; ++i){
                if(vi[i] < t) continue;
                for(int j=0; j<=2000; ++j){
                    //if(j-vi[i]+t >= 0)
                        dp[t][j]=min(dp[t][j], dp[t][j-vi[i]+t]+ct[i]);
                    //else
                        //dp[t][j]=min(dp[t][j], ct[i] );
                }
            }
        }
        ll ans=0;
        for(int i=0; i<=10; ++i){
            for(int j=2000; j>=1; --j){
                if(dp[i][j]<=dp[i][j-1]){
                    dp[i][j-1]=dp[i][j];
                }
            }
        }
        int flag=0;
        for(int i=1; i<=n; ++i){
            if(dp[b[i]][a[i]] >= inf) flag=1;
            else ans+=dp[b[i]][a[i]];
        }
        if(flag) printf("-1\n");
        else printf("%I64d\n",ans);
    }
    return 0;
}

 

posted on 2017-08-05 14:28  lazzzy  阅读(333)  评论(0编辑  收藏  举报

导航