青蛙的约会<数论,extgcd>
来源:互联网 发布:淘宝运作流程 编辑:程序博客网 时间:2024/05/16 02:11
青蛙的约会
题意:
在一个圆上有一个零刻度点,公青蛙和母青蛙分别在A点和B点<不同的位
置>,他们每秒行走的距离分别是m和n,圆的周长是L。问题是这两个青
蛙能不能相遇,若能在什么时候相遇?
解:
<对于初学者来说,解得过程是漫长的>假设可以相遇,相遇的时间是x,并且相遇的时候快的比慢的多了圈,则可得方程:(A+m*X)-(B+n*X)=Y*L:里得算法。
什么是扩展欧几里得?
extgcd:
如何求aX+bY=C的一个解?令d=gcd(a,b);等式两边同时除d,a/d*X+b/d*Y=C/d.这里有一个pint,a、b除以d一定是整数,但是c不一定,如果c/d不是整数,那么说明青蛙不能相遇,无解。易知道,a*X0+b*y0=d,<一定有解>有解(x0,y0)
定理一:如果d = gcd(a, b),则必能找到正的或负的整数k和l,使d = a*k + b*l。
。两边同时乘上C/d.得a*(C/d*X0)+b*(C/d*y0)=c。得一解,x=C/d*X0,y=C/d*y0。扩展欧几里得的作用是什么呢?求x0,y0,和d。
void extgcd(LL a,LL b,LL&d,LL &x,LL &y){ if(!b){d=a;x=1,y=0;} else{ extgcd(b,a%b,d,y,x); y-=x*(a/b); }}
具体是这样:递归
由于gcd(a, b) = gcd(b, a%b) ,有ax0 + by0 = gcd(a, b) = gcd(b, a%b) = bx1 + (a%b)y1,而a%b又可以写成a-a/b*b,所以=bx1 + (a-a/b*b)y1 = ay1 + b(x1-a/b*y1),所以如果我们求出gcd(b, a%b) = bx1 + (a%b)y1的x1和y1,那么通过观察就可以求出x0 = y1,y0 = (x1 - a/b*y1)。那我们怎样求x1和y1呢?当然是求x2和y2了,做法一样的。一直求到gcd(an, 0) = an*xn + 0 * yn,这时令xn=1,yn=0就完事了,就可以求xn-1和yn-1,然后xn-2和yn-2,然后一直求到x0和y0了。
定理二:若gcd(a, b) = 1,则方程ax ≡ c (mod b)在[0, b-1]上有唯一解。
定理三:若gcd(a, b) = d,则方程ax ≡ c (mod b)在[0, b/d - 1]上有唯一解。
上面说过,这个该死的方程等价于ax + by = c,如果有解,两边同除以d,就有a/d * x + b/d * y = c/d,即a/d * x ≡ c/d (mod b/d),显然gcd(a/d, b/d) = 1,所以由定理二知道x在[0, b/d - 1]上有唯一解。所以ax + by = c的x在[0, b/d - 1]上有唯一解,即ax ≡ c (mod b)在[0, b/d - 1]上有唯一解,得证!
如果得到ax ≡ c (mod b)的某一特解X,那么我令r = b/gcd(a, b),可知x在[0, r-1]上有唯一解,所以我用x = (X % r + r) % r就可以求出最小非负整数解x了!(X % r可能是负值,此时保持在[-(r-1), 0]内,正值则保持在[0, r-1]内。加上r就保持在[1, 2r - 1]内,所以再模一下r就在[0, r-1]内了)
#include<iostream>#include<cstdio>using namespace std;typedef long long LL;void extgcd(LL a,LL b,LL&d,LL &x,LL &y){ if(!b){d=a;x=1,y=0;} else{ extgcd(b,a%b,d,y,x); y-=x*(a/b); }}int main (){ LL x,y,m,n,L,d,r,X,Y; while(~scanf("%lld%lld%lld%lld%lld",&x,&y,&m,&n,&L)) { extgcd(n-m,L,d,X,Y);r=L/d; if((X-Y)%d)printf("Impossible\n"); else printf("%lld\n",((X-Y)/d*x%r+r)%r); } return 0;}
来源+整理
- 青蛙的约会<数论,extgcd>
- 青蛙的约会 (数论)
- POJ1061 - 青蛙的约会 - 数论
- 青蛙的约会(数论)
- POJ1061 青蛙的约会 数论
- [poj1061][数论]青蛙的约会
- 1061 青蛙的约会 数论 扩展GCD
- poj 1061 青蛙的约会 数论
- ACM 数论 青蛙的约会 扩展欧几里得
- poj 1061 青蛙的约会(数论)
- 数论之青蛙约会
- poj 1061青蛙的约会 (数论:扩展的欧几里得算法)
- poj 1061 青蛙的约会 数论 线性同余
- 青蛙的约会——欧几里得—数论
- [数论]POJ 1061 青蛙的约会 扩展欧几里得算法
- Poj 1061 青蛙的约会 数论 欧几里得 求余方程
- POJ1061_青蛙的约会(数论/同余方程)
- 青蛙的约会 ---- 同余方程(数论)
- 哈理工OJ 1559 线段相交(计算几何)
- JQuerySelectors
- 在androidMainfest.xml文件中在此Activity中写入 android:windowSoftInputMode="adjustPan" 可以让界面不被弹出的键盘挤上去。
- 深入理解Java的接口和抽象类
- Linux下出现No module named ..的原因
- 青蛙的约会<数论,extgcd>
- scala笔记(一)
- angular js知识总结
- android网络框架
- Objective-C 编程全解-第02章 Objective-C程序设计
- IDM张檬版
- R语言实战-基本数据管理
- JavaScript学习笔记04-函数
- 第一篇技术博客