877. 扩展欧几里得算法

裴蜀定理

对于任意正整数a,b,一定存在一组正整数x和y,使得xa + yb = (a, b),并且(a, b)是a和b能凑(系数>0)出来的最小正整数。

为什么是最小?

因为a和b的最大公约数是(a, b),所以xa + yb = k(a, b)必定成立,又因为k是整数, a, b, x, y > 0, 所以k >= 1, 所以(a, b)是xa + yb的最小值。

而裴蜀定理的证明可以用构造的方法来证明,即对于任意一个a, b都能找到x,y使得ax + by = (a, b),求x,y可以用扩展欧几里得算法求。

首先复习一下递归版欧几里得算法,求最大公约数的:

int gcd(int a, int b){
	if(b == 0) return a;
	if(a < b) return gcd(b, a);
	return gcd(b, a % b);
}

而扩展欧几里得算法就是要在求(a, b)的时候顺便把x和y求出来。

过程:

\(xa + yb \\= gcd(a, b)\\=gcd(b, a \% b)\)

对于b和a % b,存在p和q使得

\(pb+q(a\%b) = gcd(b, a\%b)\)

由上式得\(pb+q(a\%b) = gcd(a, b)\)

\(gcd(a, b) = d\)

那么\(xa + yb \\= pb + q(a \% b)\\=pb + q(a - \lfloor a/b\rfloor b)\\=qa+(p-q\lfloor a/b\rfloor)b\)

所以\(x = q\\y=p-q\lfloor a/b\rfloor\)

由此得到递归本层和下一层得关系

可得代码

int exgcd(int a, int b, int &x, int &y){
	if(b == 0){
		x = 1, y = 0;
		return a;
	}
	int d = exgcd(b, a % b, y, x);
	y -= a / b * x;
	
	return d;
}

这样就同时得到了x,y和d,并且注意a对应得是x,b对应y,注意传参顺序。

posted @ 2020-09-21 18:38  yys_c  阅读(173)  评论(0)    收藏  举报