扩展欧几里得 + 线性同余方程

总结自这两篇:👨‍✈️👩‍💼

mark一下这篇:👨‍🚀

一、扩展欧几里得

1. 辗转相除法(欧几里得算法)的证明:

1 int gcd(int a,int b){
2    return b?gcd(b,a%b):a;
3 }
4 // 不用考虑a,b大小,会自己交换的

2. Ex_gcd用途:求关于 ax + by =gcd(a,b) 的所有整数解

     思路:令g=gcd(a,b) ,若我们已知该方程一个特解x0,y0,则我们可以用某种方式求出所有整数解。

裴蜀定理:对任何整数a,b,m,关于未知数x,y的裴蜀等式ax +by = m, 当且仅当m为(d=gcd(a,b))的倍数时有整数解

3. ①怎么求出这个特解?

  已知gcd(a,b) = gcd(b, a%b) 接下来讨论下两式有无关系

       a * x1 + b * y1 = g(a,b)
       b * x2 + (a%b) * y2 = g(b,a%b)

可知:a * x1 + b * y1 = b * x2 + (a%b) * y2=b * x2 + (a - (a / b) * b) * y2= a * y2 + b * (x2 - (a / b) * y2)

所以可知:x1=y2, y1=x2 - (a/b)*y2 

则知道x2, y2 就可以知道x1, y1了。

因为最终辗转相除法递归出口是b=0,a为GCD,所以对 a*x+b*y=gcd(a,b) 来说,x=1,y=0;得到这个特解,在回溯回去,就可以得出原方程的一个特解

 ②如何由该特解推出其他整数解?

 a*(x+b/g)+b*(y-a/g)=g; a*b/g是lcm(a,b)  然后通过这样改变x,y的值,来求出所有x,y的通解。

 1 void e_gcd(int a,int b,int &gcd,int &x,int &y)
 2 {
 3     if(b==0)
 4     {
 5         x=1;
 6         y=0;
 7         gcd=a;
       return;
8 } 9 else 10 { 11 e_gcd(b,a%b,gcd,y,x); // x2=y1-(a-b)*y2, y2=x1 12 y-=x*(a/b); 13 } 14 }

4. 对于a*x + b*y =c求解:如果c%gcd(a,b)!=0, 即 c 不是 gcd 的整数倍,则无解。如果 c % gcd(a,b) == 0 且 c / gcd(a,b) = t,那么求出方程 a * x + b * y = gcd(a,b) 的所有解 x,y,将 x,y 乘上 t,对应的 x’,y’即是方程 a * x + b * y = t * gcd(a,b) 的解

5. 求最小正整数解:  联系 3.② 

 1 // 第一种,朴素循环法 
 2        e_gcd(n-m,l,g,s,k);
 3        ll t=(x-y)/gg;
 4        s=s*t;
 5        t=abs(l/gg);
 6        if(s<=0){
 7           while(s<0) s+=abs(t);
 8           }
 9        else
10           {
11           while(s>0) s-=abs(t);
12           s+=abs(t);
13           }     
1 // 第二种,
2        e_gcd(n-m,l,g,s,k);
3        ll t=(x-y)/gg;
4        s=s*t;
5        t=abs(l/gg);
6        s=(s%t+t)%t; //加t是为了防负

 

二、线性同余方程

1. ax≡b (mod n) 意思是 ax%n==b%n ,可以被写为ax+ny=b ( (ax-b)%n=0 => (ax-b) - (ax-b)/n*n=0 其中y=-(ax-b)/n ,b代表次数,最后取绝对值即可)

   此方程有解当且仅当 b 能够被 a 与 n 的最大公约数整除(记作 gcd(a,n) | b 即 b%gcd(a,n) == 0)。

 如果x0是一个解,那么所有的解可以表示为:{x0+kn/d|(k∈z)}  //d 是a 与 n 的最大公约数;kn/d即b/gcd (3.②)。在模 n 的完全剩余系 {0,1,…,n-1} 中,恰有 d 个解。

2. 所以由上可知,只要求出一个特解,就可以求出通解,所以要用到exgcd。

 

三、 tips

1. 写懵了,看了半天才反应过来。 如果题目说ax+by=1,那判断条件就是g是否为1,这样后面x加b/g也不用写这个g了。

posted @ 2019-07-20 13:08  XXrl  阅读(267)  评论(0编辑  收藏  举报