求解线性同余方程

定理1:对于方程 a * x + b * y = c,该方程等价于 a * x ≡ c (mod b),有整数解的充分必要条件是:
c % GCD(a,b) = 0。

根据定理1,对于方程 a * x + b * y = c,我们可以先用扩展欧几里德算法求出一组Xo、Yo,也就是 a * Xo + b * Yo = GCD(a,b),然后两边同时除以 GCD(a,b) ,再乘以c。这样就得到了方程
a * Xo * c/GCD(a,b) + b * Yo * c/GCD(a,b) = c,我们也就找到了方程的一个解。

定理2:若 GCD(a,b) = 1,且Xo、Yo为 a * x + b * y = c的一组解,则该方程的任一解可表示为:
x = Xo + b * t,y = Yo - a * t,且对任一整数 t 皆成立。

根据定理2,可以求出方程的所有解。但实际问题中,我们往往被要求去求最小整数解,也就是求一个特解x,t = b/GCD(a,b),x = (x%t + t)%t。

代码实现如下:

int extended_gcd(int a, int b, int &x, int &y)
{
	if( !b )  // b==0
	{
		x = 1;
		y = 0;
		return a;
	}
	
	int ret = extended_gcd(b, a%b, x, y);
	int tmp = x;
	x = y;
	y = tmp - a/b*y;
	return ret;
}


//用扩展欧几里得算法解线性方程 ax + by = c;
bool linearEquation( int a, int b, int c, int &x, int &y)
{
	int d = extended_gcd(a,b,x,y);
	if(c%d) return false;
	int k = c/d;
	X *= k;  // + t*b;
	y *=k;   // - t*a;
    //求的只是其中一个解
	return true;
}

提示1:设a, b, c为任意整数。若方程 ax+by=c 的一组整数解为 (Xo, Yo),则它的任意整数解都可以写成 ( Xo+kb’ , Yo-kb’ ),其中 a’ = a/gcd(a,b),b’ = b/gcd(a,b),k取任意整数。

提示2:设 a,b,c 为任意整数,g = gcd(a,b),方程ax+by=g 的一组解是(Xo,Yo),则当c是g的倍数时 ax+by=c 的一组解是(Xo c/g, Yo c/g),当c不是g的倍数时无整数解。

猜你喜欢

转载自blog.csdn.net/qq_42815188/article/details/88119748