[传智杯]补刀

题目描述
UIM 在写程序的空闲玩一款 MOBA 游戏。

当敌方的小兵进入到我方防御塔的范围内,就会持续受到防御塔造成的伤害;当然我方英雄也可以对它造成伤害。当小兵的血量降到了 0 或者更低,就会被击杀。为了获得经验,UIM 希望在防御塔将这个小兵杀死之前,亲自补刀将其击杀。

为了简化问题,我们假设这个小兵有 h 点的生命值。每次防御塔的攻击可以给小兵造成 x 点伤害,而你的英雄每次攻击可以给小兵造成 y 点伤害。你的攻击速度和防御塔攻击速度相同,所以你可以在防御塔第一次攻击小兵之前,或者每次防御塔攻击之后,选择是否对小兵进行一次攻击,当然你也可以选择不攻击。

现在想知道,给出这些信息,判断英雄是否有办法将这个小兵击杀?

输入

每个测试点由多组数据组成。

输入第一行,包含一个正整数 T,表示数据组数。

接下来 T 行,每行三个非负整数 h,x,y,其意义已经在题目描述中给出。

输出

输出 T 行。对于每组数据,如果可以最后将小兵击杀,输出 Yes  否则输出 No

样例输入

5
100 100 1
100 97 1
100 98 1
100 99 1
100 100 0

样例输出

No
No
Yes
Yes
No

提示

数据的组数不多于 501<= h <=10^180<= x,y <= 10^18

题目的思路很简单,首先进行判断,如果y=0,那么自己的英雄不可能造成伤害,输出No;如果x=0,防御塔不会对对方造成伤害,输出yes。其它的情况。tmp表示h/x的值,代表的含义是在英雄不主动攻击的情况下,防御塔可以对小兵攻击tmp次而不造成对方死亡。这里需要考虑x能整除h的情况,需要将tmp减一。如果只有防御塔进行攻击,那么在tmp+1次攻击时,就会将对方击杀。
防御塔发动tmp次攻击,则英雄有tmp+1次攻击的机会。只要这tmp+1次攻击的伤害总和大于小兵遭受防御塔tmp次攻击后剩余的生命值,英雄就能够拿到经验。否则就拿不到。
这道题最坑人的地方就是数据量,数据量是10^18,虽然long long类型只能够表示部分10的18次方数量级的数不能够表示所有10的18次方的数。所以要改用unsigned long long 类型。
代码:

#include<iostream>
#include<algorithm>
using namespace std;
int main()
{
    
    
	int T;
	unsigned long long h,x,y;
	cin>>T;
	while(T--){
    
    
		cin>>h>>x>>y;
		if(y<=0)cout<<"No"<<endl;
		else if(x<=0)cout<<"Yes"<<endl;
		else{
    
    
			unsigned long long tmp; //商 
			if(h%x!=0)
				tmp=h/x;
			else
				tmp=h/x-1;
			
			if((tmp+1)*y>=h-tmp*x)cout<<"Yes"<<endl; 
			else cout<<"No"<<endl;
		}
	}
	return 0;
}

猜你喜欢

转载自blog.csdn.net/weixin_45382645/article/details/109017607