题目
求两个数的最大公约数。
怎么看都是一个数学的问题,所以还是需要数学的定理公理,来求。
辗转相除法
假设两个整数x,y
(x>y
)
那么:
两个数相除商:k=x/y
两个数相除余数:d=x%y
那么使用y表x:x=ky+b
所以如果一个数能够正除y、x,那么这个数一定能够正除b
。
假设两个数的最大公约数为c
,那么x=mc=ky+b
,y=nc
。
所以b=x-ky=mc-knc=c(m-kn)
所以,c
也是b
的一个因数。
参考文章
所以得出
int gcd(int x,inty)
{
return(!y)?x:gcd(y,x/y);
}
也就是
f(42,30)=f(30,12)=f(12,6)=f(6,0)=6
方法二
改进方法一
对于取模运算开销大,所以将上面的取模运算改为减法
int gcd(int x, int y)
{
if(x<y)
{
return gcd(y,x)
}
if(y == 0)
{
return x;
}else{
return gcd(x-y,y);
}
}
当时对于(100000,1)这种计算缓慢
方法三
利用2来简化计算。如果两个数都是偶数,那么同除2。
如果其中一个数是偶数,那么该数除2,另一个不变。
如果都不是偶数,那么直接相减,然后递归。
看不太懂,不过方法却是对。
网友评论