涂色游戏

D e s c r i p t i o n Description Description

你有 1 0 20 10^{20} 1020个格子,它们从 0 0 0 开始编号,初始时所有格子都还未染色,现在你按如下规则对它们染色:
编号是 p 1 p_1 p1倍数的格子(包括 0 0 0 号格子,下同)染成红色。
编号是 p 2 p_2 p2倍数的格子染成蓝色。
编号既是 p 1 p_1 p1倍数又是 p 2 p_2 p2倍数的格子,你可以选择染成红色或者蓝色。
其中 p 1 p_1 p1 p 2 p_2 p2是给定的整数,若格子编号是 p 1 p_1 p1 p 2 p_2 p2的倍数则它必须要被染色。在忽略掉所有未染色格子后,你不希望存在 k k k 个连续的格子颜色相同,因为你认为这种染色方案是无聊的。现在给定 p 1 p_1 p1, p 2 p_2 p2 , k k k,你想知道是否有一种染色方案不是无聊的。

I n p u t Input Input

本题包含多组数据。
第一行一个整数 TT 表示数据组数。
每组数据一行三个正整数 p 1 p_1 p1 , p 2 p_2 p2 , k k k,变量意义见题目描述。

O u t p u t Output Output

对于每组数据,输出一行一个字符串,若存在一种染色方案不是无聊的,则输出 YES,否则输出 NO。
选手程序输出结果与样例或题面中的一种格式相符即可,即不区分大小写。例如,如果标准答案为 Y E S YES YES ,则输出结果 Y E S / Y e s / y e s YES/Yes/yes YES/Yes/yes 都视为正确。

S a m p l e Sample Sample I n p u t Input Input#1
4
2 10 4
2 3 6
1 4 7
1 1 2
S a m p l e Sample Sample I n p u t Input Input#2
8	
370359350 416913505 3
761592061 153246036 6
262185277 924417743 5
668232501 586472717 2
891054824 169842323 6
629603359 397927152 2
2614104 175031972 68
924509243 421614240 4
S a m p l e Sample Sample O u t p u t Output Output#1
No
Yes
Yes
Yes
S a m p l e Sample Sample O u t p u t Output Output#2
Yes
Yes
Yes
No
No
No
Yes
Yes

H i n t Hint Hint

对于所有测试点: 1 ≤ T ≤ 1 0 6 1 \leq T\leq 10^6 1T106 1 ≤ p 1 , p 2 , k ≤ 1 0 9 1\leq p_1,p_2,k\le 10^9 1p1,p2,k109

思 路 思路

其实差不多就是在 0 − p 2 0-p_2 0p2里面求可以有多少个 p 1 p_1 p1的倍数
若其间含有最多的倍数超过了k那么就NO
然后我们要求其间最多有多少个 p 1 p_1 p1的倍数
假设0和 p 2 p_2 p2为蓝色
1为 p 1 p_1 p1的倍数,然后接下来就是 1 + p 1 1 + p_1 1+p1 1 + p 1 ∗ 2 1 + p_1 * 2 1+p12……
这种情况下
0和 p 2 p_2 p2 p 1 p_1 p1的倍数是最多的
那怎么求呢
其实可以转换为以1为第一个 p 1 p_1 p1的倍数
然后接下来第 k − 1 k-1 k1 p 1 p_1 p1的倍数是否大于 p 2 p_2 p2
如果大于那么就没有连续k个数是相同的颜色
注意:数据过大,可以先约分再计算
要特判 k = 1 k=1 k=1的情况

#include<algorithm> 
#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
#define ll long long
ll n, x, y, z, t;
ll gcd(ll a, ll b)
{return (!b) ? a : gcd(b, a % b);}
int main()
{
//	freopen("1.out", "w", stdout);
	scanf("%lld", &n);
	while(n--)
	{
		scanf("%lld%lld%lld", &x, &y, &z);
		if (x > y){t = x;x = y;y = t;}
		t = gcd(x, y);
		x /= t, y /= t;//约分
		if(1 + x * (z - 1) < y || z == 1)printf("No\n");
		else printf("Yes\n");
	}
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值