我们在学习编程或者是在学习后进行课后习题练习的时候经常会碰见一种类型的题目,也就是去计算两个数的最大公约数或者是两个数的最小公倍数。这时我们虽然对这两个概念比较了解,小学的时候也经常碰见这种题目,可是仿佛不知道为什么,就是我们用编程解答的时候,就不知道该去怎么样去计算这些知识了,所以今天我们就来探讨以下最大公约数和最小公倍数的求法。
概念
我们既然要去求这两个数,那么首先我们就必须要去了解下这两个数的概念。这两个数的概念也是如下:
最大公约数:指能够整除多个整数的最大正整数,而多个整数不能都为零,例如8和12的最大公约数为4;
最小公倍数:两个或多个整数公有的倍数叫做它们的公倍数,其中除0以外最小的一个公倍数就叫做这几个整数的最小公倍数,例如6和24的最小公倍数为24。
这里我们已经了解到了最大公约数和最小公倍数是什么了,那接下来我们就要去使用我们的编程去实现从给出的两个数中求得其最大公约数和最小公倍数了。
最大公约数
根据约数的定义可知,某个数的所有约数必不大于这个数本身,几个自然数的最大公约数必不大于其中任何一个数。所以我们要求的两个正整数中的最大公约数肯定不大于其两者中的任何一个,并且又可以同时整除两个整数的最大自然数。
那么我们得知以上思路以后我们就可以去计算最大公约数了阿。
穷举法
首先我们最简单的方法就是穷举法来求两个数的最大公约数
算法思路:按照从大(两个整数中较小的数)到小(到最小的整数1)的顺序求出第一个能同时整除两个整数的自然数,即为所求。
#include<stdio.h> int main() { int m, n, temp, i; printf("请输入任意2个数:\n"); scanf("%d%d", &m, &n); if(m<n) //判断大小,使m一定不小于n { temp=m; m=n; n=temp; } for(i=n; i>0; i--) if(m%i==0 && n%i==0) //满足同时整除的条件 { printf("%d\n",i); return 0 ; } }
这种方法虽然清晰易懂,可是其非常慢,有时需要遍历所有的数才行,那么这时我们就要想办法去改进这个算法了,那么这时我们可能会想起,小时候计算公约数的时候使用的方法:辗转相除法。
辗转相除法
辗转相除法是求最大公约数的一种方法。它的具体做法是:用较小数除较大数,再用出现的余数(第一余数)去除除数,再用出现的余数(第二余数)去除第一余数,如此反复,直到最后余数是0为止。如果是求两个数的最大公约数,那么最后的除数就是这两个数的最大公约数。
举个例子就是:比如两个数字,x=453,y=36;
453%36=21;
36%21=15;
21%15=6;
15%6=3;
6%3=0;
%是取余符号,大家应该都知道吧。所以用这个算法可以求出453和36的最大公约数是3;
大概的流程就是这样,我们发现使用这个方法后,会大大提高我们的计算效率,也可以减低其复杂度。
那么我们实现函数就如下:
int gcd(int a, int b){ //若a<b,那么交换两变量的值 if(a < b){ int temp1 = a; //块级变量 a = b; b = temp1; } //求最大公约数 while(b!=0){ int temp2 = b; //块级变量 b = a % b; a = temp2; } return a; }
也是先进行两个数之间的大小比较,之后再根据我们的辗转相除法去进行计算就可以了。
那么整体的代码就是这样的:
#include <stdio.h> //函数声明 int gcd(int a, int b); int main() { printf("The greatest common divisor is %d\n", gcd(100, 60)); return 0; } //函数定义 int gcd(int a, int b){ //若a<b,那么交换两变量的值 if(a < b){ int temp1 = a; //块级变量 a = b; b = temp1; } //求最大公约数 while(b!=0){ int temp2 = b; //块级变量 b = a % b; a = temp2; } return a; }
最小公倍数
对于最小公倍数的求法,在我们知道了最大公约数之后计算起来也就很简便了。求最小公倍数相对来说就比较简单了。只需要先求出最大公约数。用两个数的乘积除以最大公约数即可。
因为如果找到了两个数a,b的最大公约数c,那么假设a=mc,b=nc,那么可以肯定,n,m没有公约数,这里暂且称之为“互质数”,即m,n相互之间的关系相当于两个质数之间的关系。那么求a,b的最小公倍数,就相当于求m,n的最小公倍数。我们令mx=ny=c, 则m/n=y/x。则y=km,x=kn。要使mx最小,也就是ny最小,则mkn最小,则k=1时mkn最小,则mn最小,同理,ny当y=m时也最小,所以n,m的最小公倍数就是nm。
所以最小公倍数的求法也就是:最小公倍数=两数的乘积/最大公约(因)数
那么我们的代码实现也就如下:
#include <stdio.h> int get_LCM(int a,int b); int main() { int a; int b; while((scanf("%d%d",&a,&b))!=EOF){ printf("%d\n",get_LCM(a,b)); } return 0; } int get_LCM(int a,int b) { int temp; int remainder; int A; int B; A=a; B=b; if(a<b) { temp=a; a=b; b=temp; } while(a%b){ remainder=a%b; a=b; b=remainder; } return A*B/b; }