首先基础介绍一下拓展欧几里得。
所谓的拓展欧几里得就是求解ax+by=c的x的最小整数解。
当且仅当 c%gcd(a,b)==0时有解。
设 ax1+by1=gcd(a,b) , bx2+a%by2=gcd(b,a%b), 根据欧几里得定理 gcd(a,b)=gcd(b,a%b)
所以 ax1+by1=bx2+(a-b*a/b)y2=ay2+b(x2-a/b*y2)
所以 x1=y2 , y1= x2-a/b*y2 无限递归下去只到 b=0.
接着设中间变量 s=b/gcd(a,b) x=x*c/gcd(a,b)
则 x=(x%s+s)%s 为最小整数解。
对于本题,设跳跃步数为t。 根据运动学规律,路程相差整数倍则两青蛙相遇。则 (x+m*t)-(y-n*t)=kl -> (n-m)t+kl=(x-y) -> At+Bk=C
代码:
#include"cstdlib"
#include"cstdio"
#include"cstring"
#include"cmath"
#include"queue"
#include"algorithm"
#include"iostream"
using namespace std;
__int64 exgcd(__int64 a,__int64 b,__int64 &x,__int64 &y)
{
if(b==0)
{
x=1;
y=0;
return a;
}
__int64 r=exgcd(b,a%b,x,y),t;
t=x;
x=y;
y=t-a/b*y;
return r;
}
int main()
{
__int64 x,y,m,n,l;
while(cin>>x>>y>>m>>n>>l)
{
__int64 s,t,k,gcd;
gcd=exgcd(n-m,l,t,k);
if((x-y)%gcd!=0)
{
puts("Impossible");
continue;
}
s=l/gcd;
t=t*(x-y)/gcd;
t=(t%s+s)%s;
printf("%I64d\n",t);
}
}