欧几里德是用来求最大公约数的,可以把它看成是状态转移,
对任意两个数a,b(a>b),d=(a,b),如果b不为零,那么(a,b)=(b,a%b)
证明: 令 r=a%b,即存在k,使得 a=b*k+r,那么r=a-b*k;显然r>=0, r%d=((a%d)-(b*k)%d)%d,因为a%d=b%d=0,所以r%d=0;
因此求(a,b)可以转移到求(b,a%b),那么这就是个递归过程了,那什么时候递归结束呢,想一下,a,b不能为零,则可以把当b为零,作为递归的结束(当然还可以以其它结束条件),这就是求最大公约数的方法可以以其它结束条件),这就是求最大公约数的方法
int (int a,int b)
{
if(b==0)return a;
else return (b,a%b);
}
理解了上面,那么扩展欧几里得就能很容易理解了,对任意a,b(a>b),我们列出这样一个式子: a*x+b*y=(a,b);
不要觉得扩展欧几里得很牛逼,它就是一个算x,y的一个方法,只是在上面中多了处理x,y的步骤
我们这样来想:
已知当前的一个状态:a1 b1 x1 y1, a1*x1+b1*y1=(a1,b1),注意这里的a1,b1是求(a,b)中的一个状态,
假设 (a1,b1)是由(a0,b0)转移过去的
那么: a1=b0 ; b1=a0%b0=a0-k*b0 (k=int(a0/b0));(a0,b0)=(a1,b1);
代入a1*x1+b1*y1=(a1,b1),变化成:b0*x1+(a0-k*b0)*y1=(a1,b1)=(a0,b0);
a0*y1+b0*(x1-k*y1)=(a0,b0);
这样可以得到: x0=y1; y0=x1-k*y1;(理解这个过程了么,由当前状态可以算出上一状态的x,y,即当前状态可以由它的下一个状态的x,y得到)
code:
int exGcd(int a,int b,int &x,int &y)
{
if(b==0)
{
x=1;
y=0;
return a;// 此时a是最开始(a,b)的最大公约数,那么 (a,b)*1+ 0*0=(a,b),肯定对的,在这里,我认为,y可以为任何值都对
}
int d=exGcd(b,a%b,y,x);
y-=a/b*x;
return d;//返回最大公约数
}
应用:
扩展欧几里得算法的应用基本全都是基于:a*x+b*y=d 这个式子来发散的
因篇幅问题不能全部显示,请点此查看更多更全内容
Copyright © 2019- stra.cn 版权所有 赣ICP备2024042791号-4
违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com
本站由北京市万商天勤律师事务所王兴未律师提供法律服务