提起求最大公约数数的算法,那么很多人都会想起辗转相除法,即欧几里德算法,算法思想如下:
给定两个整数a,b,求a和b的最大公约数,若d是a和b的公约数,则a也是b和a%b的公约数,相反如果a是b和a%b的公约数,那么b也是a和b的公约数,利用这个思想,算法实现如下:
int gcd(int a, int b) { int t, r; if(a < b){ t = a; a = b; b = t; } while(b != 0) { r = b; b = a % b; a = r; } return a; }
1.若a和b都是偶数,则记录下公约数2,然后都除2(即右移1位);
2.若其中一个数是偶数,则偶数除2,因为此时2不可能是这两个数的公约数了
3.若两个都是奇数,则a = |a-b|,b = min(a,b),因为若d是a和b的公约数,那么d也是a-b和min(a,b)的公约数。
基于以上的原理,递归算法实现如下:
int sgcd(a, b) { int t; if(a < b){ t = a; a = b; b = t; } if(b == 0) return a; if(a % 2 == 0 && b % 2 == 0){ return 2 * sgcd(a / 2, b / 2); } else if(a % 2 == 0 && b % 2 != 0){ return sgcd(a / 2, b); } else if(a % 2 != 0 && b % 2 == 0){ return sgcd(a, b / 2); } else { return sgcd(a-b, b); } }
参考:
http://www.cnblogs.com/drizzlecrj/archive/2007/09/14/892340.html
http://blog.henix.info/blog/stein-gcd-algorithm.html