zoukankan      html  css  js  c++  java
  • 解同余式的最小解

      我们知道欧几里得扩展定理是同余方程ax≡b(mod c)解得有力方法。这个方程可能有解也可能没有解,下面给出有解的条件:

      定理:同余方程ax≡b(mod c)有解,当且仅当gcd(a,c)|b,且方程有gcd(a,c)个解。

      原因是求ax≡b(mod c)可以转化为求ax+cy=b。

      令:d=gcd(a,c),  k=c/d;

      我们可以用扩展欧几里得求出x,y值。那么方程ax≡b(mod c)的一个特解:x0=x*(b/d)%c。并且它的d个解分别为:

      Xi=(x0+i*(k))%c,{i=0,1,2,.....d-1}。

      方程ax≡b(mod c)的最小解为:(x0%k+k)%k。

    代码如下:

     1 #include <cstdio>
     2 #include <cstring>
     3 #include <cmath>
     4 using namespace std;
     5 
     6 __int64 Exgcd(__int64 a, __int64 b, __int64 &x, __int64 &y)
     7 {
     8     if(b==0)
     9     {
    10         x=1, y=0;
    11         return a;
    12     }
    13     __int64 r = Exgcd(b, a%b, x, y);
    14     __int64 tp=x;
    15     x = y;
    16     y = tp-a/b*y;
    17     return r;
    18 }
    19 
    20 // ax==b(mod c)
    21 void Liner_modu(__int64 a, __int64 b, __int64 c)
    22 {
    23     __int64 x, y, ans;
    24     __int64 d = Exgcd(a, c, x, y);
    25     if(b%d)
    26     {
    27         puts("No solution");
    28         return;
    29     }
    30     ans = x*(b/d)%c;  //特解
    31     y = c / d;
    32     ans = (ans%y+y)%y; //最小解
    33     printf("%I64d
    ", ans);
    34 }
    35 int main()
    36 {
    37     __int64 a, b, c;
    38     while(~scanf("%I64d%I64d%I64d", &a, &b, &c))
    39     {
    40         while(a<0) a+=c;
    41         while(b<0) b+=c;
    42         Liner_modu(a, b, c);
    43     }
    44     return 0;
    45 }
  • 相关阅读:
    JavaScript跨域总结与解决办法
    css IFC 与 BFC分析
    JavaScript Note
    Knowledge Architecture
    BSP
    Olympiad
    Software Engineering
    Assembly Language
    Algorithm
    Data Structure
  • 原文地址:https://www.cnblogs.com/khan724/p/4149480.html
Copyright © 2011-2022 走看看