次芝麻

题目大意:

今有两数(a,b),进行(k)轮对抗,每轮对抗规则如下:

每次取(a,b)中较小者,从较大者中减去其本身的值,并使其值翻倍.

现给出(a,b,k),请你求出(k)轮对抗后其较小者之值.

solution:

通过打表可以发现,答案具有循环节且长度不超过(frac{(n+m)}{2}),于是暴力枚举跑循环节即可得60分.(燃鹅我只水了50分)

此题十分神奇,满分解法耐人寻味,下面让我们来模拟一轮.

假设有两个数(n,m)进行一轮对抗,其中(ngeq m),那么可以得出,对抗后得到的两个数为(2m,n-m),我们将其放在模((m+n))意义下,可以发现,(n-m=2nmod (m+n)),于是每轮对抗可看作将(m,n)分别乘上(2)再模((m+n)),快速幂求解即可.

code:

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
#include<map>
#define R register
#define next kdjadskfj
#define debug puts("mlg")
#define mod 1004535809
#define Mod(x) ((x%mod+mod)%mod)
using namespace std;
inline ll Qpow(ll _,ll __,ll ____){ll ___=1;for(;__;__>>=1){if(__&1) ___*=_,___%=____;_*=_;_%=____;}return ___;}
ll n,m,k;
int main(){	
	freopen("sesame.in","r",stdin);
	freopen("sesame.out","w",stdout);
	n=read();m=read();k=read();
	writeln(min((n*Qpow(2,k,n+m)%(n+m)),(m*Qpow(2,k,n+m)%(n+m))));
}

原文地址:https://www.cnblogs.com/ylwtsq/p/13409906.html