欧几里得算法
基本概念
欧几里得算法 \color{Green}欧几里得算法 欧几里得算法
欧几里得算法又称辗转相除法,是指用于计算两个非负整数a,b的最大公约数。
公式 :gcd( a,b ) = gcd( b,a mod b )
相关证明
代码模板
int gcd(int a, int b)
{
return b ? gcd(b, a % b): a;
}
拓展欧几里得算法
基本概念
由名字可知这是建立在欧几里得算法上的一种算法,定义如下:
给一个线性方程 ax + by = m,给出 a,b,m 求解出相应的 x 和 y 。
注意 \color{orange}注意 注意
首先,只有 m % gcd( a,b) == 0 ,即 当且仅当 m 是 a,b 最大公约数的倍数时,该线性方程才有解。
当 m 为1 时,由裴蜀定理推论可知,只有当 a,b互质才有解。
裴蜀定理 \color{Green}裴蜀定理 裴蜀定理
① 若 a, b 是整数,且 gcd(a , b) = d,那么对于任意的整数 x , y。ax+by 都一定是 d 的倍数,特别地,一定存在整数x,y,使 ax+by = d成立。
② 推论:a ,b 互质的充分必要条件是存在整数 x , y 使得 ax+by = 1 。
相关证明
证:存在整数对(x, y)使得 ax + by = gcd(a, b)
证明:
设 a > b
当 b = 0 时,a∗1 + b∗0 = gcd( a,b ) = a,此时 x = 1,y = 0 ,
当 b != 0 时,
设 a∗x1 + b∗y1 = gcd( a,b )
b∗x2 + a%b∗y2 = gcd( b,a%b )
又由于 gcd(a, b) = gcd( b,a%b )
所以有 a∗x1 + b∗y1 = b∗x2 + a%b∗y2
又因为 a%b = a − ( a / b )∗b
得到 a∗x1 + b∗y1 = a∗y2 + b∗x2 − (a/b)∗b∗y2
即 x1 = y2
y1 = x2 − (a/b)∗y2
因此可以递归的定义exgcd,同样 b = 0 时递归结束。返回最大公约数。
代码模板
int exgcd(int a, int b, int &x, int &y)
{
if( !b ) // 当 b =0 时
{
x = 1, y = 0;
return a;
}
// 当 b!=0 时
int d = exgcd( b, a%b, x, y );
int t = x;
x = y;
y = t - (a/b) * y;
return d;
}