HDU3008 Warcraft(发技能打BOSS)

Warcraft

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1766    Accepted Submission(s): 950


Problem Description
Have you ever played the Warcraft?It doesn't matter whether you have played it !We will give you such an experience.There are so many Heroes in it,but you could only choose one of them.Each Hero has his own skills.When such a Skill is used ,it costs some MagicValue,but hurts the Boss at the same time.Using the skills needs intellegence,one should hurt the enemy to the most when using certain MagicValue.

Now we send you to complete such a duty to kill the Boss(So cool~~).To simplify the problem:you can assume the LifeValue of the monster is 100, your LifeValue is 100,but you have also a 100 MagicValue!You can choose to use the ordinary Attack(which doesn't cost MagicValue),or a certain skill(in condition that you own this skill and the MagicValue you have at that time is no less than the skill costs),there is no free lunch so that you should pay certain MagicValue after you use one skill!But we are good enough to offer you a "ResumingCirclet"(with which you can resume the MagicValue each seconds),But you can't own more than 100 MagicValue and resuming MagicValue is always after you attack.The Boss is cruel , be careful!
 

Input
There are several test cases,intergers n ,t and q (0<n<=100,1<=t<=5,q>0) in the first line which mean you own n kinds of skills ,and the "ResumingCirclet" helps you resume t points of MagicValue per second and q is of course the hurt points of LifeValue the Boss attack you each time(we assume when fighting in a second the attack you show is before the Boss).Then n lines follow,each has 2 intergers ai and bi(0<ai,bi<=100).which means using i skill costs you ai MagicValue and costs the Boss bi LifeValue.The last case is n=t=q=0.
 

Output
Output an interger min (the minimun time you need to kill the Boss)in one line .But if you die(the LifeValue is no more than 0) ,output "My god"!
 

Sample Input
  
  
4 2 25 10 5 20 10 30 28 76 70 4 2 25 10 5 20 10 30 28 77 70 0 0 0
 

Sample Output
  
  
4 My god
Hint
Hint: When fighting,you can only choose one kind of skill or just to use the ordinary attack in the whole second,the ordinary attack costs the Boss 1 points of LifeValue,the Boss can only use ordinary attack which costs a whole second at a time.Good Luck To You!
 

Source
 

Recommend
gaojie   |   We have carefully selected several similar problems for you:   1158  1227  1300  1501  1502 

  题意:以魔兽为背景,给定一个英雄,英雄要打倒一个boss,英雄初始的血量与魔法值都是100,boss的血量也是100,输入n,t,p;分别表示英雄有n个技能,在每一轮双方攻击完后可以恢复t的魔法值,boss的攻击力为p。

后来n行每行两个数ai,bi(大于0小于100),表示使用技能需要的魔法值与技能的伤害(必须至少有ai的魔法值才能发动相对应的技能)。英雄也有一个普通攻击,不需要魔法值,伤害为1;

      在每一回合中都是英雄先攻击。问最少用多少回合可以打倒boss,如在打倒boss之前英雄先死了就输出My god!


       解法:因为每次boss的伤害是固定的,所以英雄死的时间也是固定的,所以如果在那个时间内不能杀死boss,就My god了。因为这题是师兄出的DP基础题,所以一开始就认定用DP做了,建立的数组dp[i][j]意思是在i轮boss剩下j血量的情况下英雄最大的魔法值为dp[j];(我一开始错误的想法是第i轮boss被扣了j血量的情况下英雄的最大魔法值dp[j],可惜错了,不知道为什么,求大神解答。。。)这思路是看其他大神博客得出的。

       因为代码没有涉及到什么算法,主要是推出那个蛋疼的状态转移方程,所以就没有什么注释,也没有什么好说的。


       网上面的DP讲座都说,最重要是搞清楚问题的决策与状态,这样才能写出状态转移方程。

        所以小弟不才,就这题说说决策与状态(如果有错望各大神指出):

具体对照代码。。。

        状态:boss剩下j血量的状态;

              决策:是否使用第K个技能使状态变成:boss剩下j - skill[k].bi血量的状态。;(当然是在能使用这技能的情况下,前面有if判断)

而决策的判断条件就是魔法值了。因为在任何一个状态下,魔法值越多,就对英雄越有利。

所以态转移方程:dp[j - skill[k].bi] = max (dp[j - skill[k].bi],dp[j] - skill[k].ai + t);

#include <stdio.h>  
#include <string.h>  
typedef struct{  
    int ai;  
    int bi;  
}node;  
int max (int a,int b)  
{  
    return a > b ? a : b ;  
}  
int main ()  
{  
    node skill[110];  
    int n,t,q,i,j,k,p;  
    int dp[110];  
    while (scanf ("%d%d%d",&n,&t,&q))  
    {  
        p = 0;  
        if (n == 0 && t == 0 && q == 0)  
            break;  
        for (i = 1 ; i <= n ; i++)  
            scanf ("%d%d",&skill[i].ai,&skill[i].bi);  
        skill[0].ai = 0;  
        skill[0].bi = 1;  
        memset (dp,-1,sizeof(dp));  
        dp[100] = 100;  
        int time = (100 % q == 0) ? 100/q : 100 / q + 1 ;//英雄在time回合内要打到boss;  
        for (i = 1 ; i <= time ; i ++)  
        {  
            for (j = 1 ; j <= 100 ; j ++)  
            {  
                if (dp[j] == -1)  
                    continue;  
                for (k = 0 ; k <= n ; k ++)  
                {  
                    if (j <= skill[k].bi && dp[j] >= skill[k].ai)  
                    {  
                        printf ("%d\n",i);  
                        p = 1;  
                        break;  
                    }  
                    else if (j > skill[k].bi && dp[j] >= skill[k].ai)  
                    {  
                        dp[j - skill[k].bi] = max (dp[j - skill[k].bi],dp[j] - skill[k].ai + t);  
                        if (dp[j + skill[k].bi] > 100)  
                            dp[j + skill[k].bi] = 100;  
                    }  
                }  
                if (p)  
                    break;  
            }  
            if(p)  
                break;  
  
        }  
        if (!p)  
            printf ("My god\n");      
    }  
}  



  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值