模板 基础数论

辗转相除法:求(a,b)的做法,原理:(a,b)=(b,a%b),当右项为0时,左项即为最大公约数。

代码:

typedef long long int64;
int64 gcd(int64 a, int64 b){
return (b == 0)? a: gcd(b, a % b);
}

扩展欧几里得算法:对于方程ax+by=gcd(a,b),求x,y最小值。

代码:

typedef long long int64;
int64 gcd_ex(int64 a,int64 b,int64& x,int64&y)
{
<span style="white-space:pre">	</span>if (b==0) {x=1;y=0;return a;}
<span style="white-space:pre">	</span>int64 d = gcd_ex(b,a%b,y,x);
<span style="white-space:pre">	</span>y=y-a/b*x;
<span style="white-space:pre">	</span>return d;
}
原理:

对于a*x+b*y=d;
递归调用时
 令a=b;b=a%b;
将其变为形式2) b*x+a%b*y=d;
           变形:b*x+a*y-(a/b)*b*y=d;
           再变:a*y+b(x-a/b*y)=d; 3)

 与2)式比较:b*x+a%b*y=d;   2)
得:
   当a=b;b=a%b时:x=y;y=x-a/b*y;

调用过程中的x,y就是对应的a,b的解;

posted on 2014-08-21 11:13  一锅土豆  阅读(89)  评论(0编辑  收藏  举报