一、最大公约数和最小公倍数

数学性质:
如果b是A和B的公约数,那么:b也是A+B的约数,即b是A,B,A+B的公约数。b也是A-B的约数,即b是A,B,A-B的公约数。更一般地,对于任意整数x、y,b也是Ax+By的约数,即b是A,B,Ax+By的公约数。
根据上一条性质,r = A - kB = A mod B,所以A mod B也是A+B的约数,即b是A,B,A mod B的公约数
用式子写出来即:

gcd(A,B) = gcd(B,A) = gcd(A,A+B) = gcd(A,A-B) = gcd(A,Ax+By) = gcd(A,A mod B)

求最大公约数有多种方法,常见的有质因数分解法、短除法、辗转相除法、更相减损法。

公式:最小公倍数*最大公约数=两个数的乘积
所以只要我们求出最大公约数,即可求出最小公倍数。(最小公倍数=两整数的乘积÷最大公约数 )

二、两个数的最大公约数

1、最简单的算法:穷举法

算法思想:从两数中较小的一数开始,依次递减,直到某个数除以两个数的余数都是0,此时这个数就是最大公约数。
代码如下:

int gcd(int x,int y)   //默认x是两数中较小的
{int t;for(t=x;t>=1;t--)  //枚举从x到1{if(x%t==0 && y%t==0)break;}return t;
}

穷举法思路简单,但是如果数据较大,耗费时间较长。

2、辗转相除法(欧几里得算法)

1、算法流程图:


辗转相除法的核心就是不断的让两个数做除法运算。其原理基于两个整数的最大公约数等于其中较小的数和两数的相除余数的最大公约数。
假设两数为 x,y。先令 z = x % y ;之后 y 赋给 x 即令 x = y ;再将 z 赋给 y 即令 y = z;辗转相减,其终止条件为:y 等于0时。

2、原理:

3、代码

非递归

int gcd(int x,int y)
{int z=y;while(x%y!=0){z=x%y;x=y;y=z; }return z;
}

递归

int gcd(int a, int b)
{return b==0 ? a : gcd(b, a%b);
}

3、更相减损法

1、算法流程图:


辗转相减法即通过对两数的不断减法运算。
假设两数为 x, y。当 x > y 时,令 x = x - y;反之,则令 y = y - x;之后一直辗转相减,直至 x = y 时,终止。

2、代码

int GCD(int a, int b)
{while(a != b){if(a > b)a = a - b;elseb = b - a;}return a;
}

改进版

int GCD(int a, int b)
{int ans = 1;      //储存第一步中约掉的若干个2int gcd;         //储存最终返回的结果 while(a%2==0  &&  b%2==0)       //如果ab均为偶数则用2约简 {a /= 2;b /= 2;ans *= 2;}//用这种方法有可能减少数字的位数,简化计算,可以省略。 while(a!=b)//判断两数是否相等,也可以理解为直到所得的减数和差相等为止{if(a>b)a -= b;     //以较大的数减较小的数elseb -= a;        //以较大的数减较小的数}gcd = a*ans;      //求第一步中约掉的若干个2与第二步中等数的乘积return gcd;         //返回gcd
}

4、三种算法对比

1.穷举法:时间复杂度是O(min(a, b)))

2.辗转相除法:时间复杂度不太好计算,可以近似为O(log(max(a, b))),但是取模运算性能较差。

3.更相减损法:避免了取模运算,但是算法性能不稳定,最坏时间复杂度为O(max(a, b)))

5、Stein算法

欧几里德算法是计算两个数最大公约数的传统算法,无论从理论还是从实际效率上都是很好的。但是却有一个致命的缺陷,这个缺陷在素数比较小的时候一般是感觉不到的,只有在大素数时才会显现出来:一般实际应用中的整数很少会超过64位(当然现在已经允许128位了),对于这样的整数,计算两个数之间的模是很简单的。对于字长为32位的平台,计算两个不超过32位的整数的模,只需要一个指令周期,而计算64位以下的整数模,也不过几个周期而已。但是对于更大的素数,这样的计算过程就不得不由用户来设计,为了计算两个超过64位的整数的模,用户也许不得不采用类似于多位数除法手算过程中的试商法,这个过程不但复杂,而且消耗了很多CPU时间。对于现代密码算法,要求计算128位以上的素数的情况比比皆是,比如说RSA加密算法至少要求500bit密钥长度,设计这样的程序迫切希望能够抛弃除法和取模。

1、算法简述

1、如果An=Bn,那么An(或Bn)Cn是最大公约数,算法结束
2、如果An=0,Bn是最大公约数,算法结束
3、如果Bn=0,An是最大公约数,算法结束
4、设置A1=A、B1=B和C1=1
5、如果An和Bn都是偶数,则An+1=An/2,Bn+1=Bn/2,Cn+1=Cn
2(注意,乘2只要把整数左移一位即可,除2只要把整数右移一位即可)
6、如果An是偶数,Bn不是偶数,则An+1=An/2,Bn+1=Bn,Cn+1=Cn(很显然啦,2不是奇数的约数)
7、如果Bn是偶数,An不是偶数,则Bn+1=Bn/2,An+1=An,Cn+1=Cn(很显然啦,2不是奇数的约数)
8、如果An和Bn都不是偶数,则An+1=|An-Bn|/2,Bn+1=min(An,Bn),Cn+1=Cn
9、n加1,转1

2、代码

递归

int GCD(int a,int b)
{if(a==b) return a;if(a==0) return b;if(b==0) return a;int k=0;while((a&1)==0&&(b&1)==0){a=a>>1;b=b>>1;k++;}while((a&1)==0&&(b&1)) a=a>>1;while((a&1)&&(b&1)==0) b=b>>1;return GCD(abs(a-b)>>1,min(a,b)<<k);
}

非递归

int SteinGCD(int a, int b) {int acc = 0;while ((a & 1) == 0 && (b & 1) == 0) {acc++;a >>= 1;b >>= 1;}while ((a & 1) == 0) a >>= 1;while ((b & 1) == 0) b >>= 1;if (a < b) { int t = a; a = b; b = t; }while ((a = (a - b) >> 1) != 0) {while ((a & 1) == 0) a >>= 1;if (a < b) { int t = a; a = b; b = t; }}return b << acc;
}

三、两个数的最小公倍数

定理:a、b 两个数的最大公约数乘以它们的最小公倍数就等于 a 和 b 本身的乘积。
由此可知,若已有了两数的最大公约数,则将两数相乘的积除以最大公约数便可得到两数的最小公倍数。

int lcm(int a,int b)
{return a/gcd(a,b)*b;   //正确的写法是先除后乘,因为a*b可能会溢出
}

四、多个数的最大公约数和最小公倍数

用辗转相除法求几个数的最大公约数,可以先求出其中任意两个数的最大公约数,再求这个最大公约数与第三个数的最大公约数,依次求下去,直到最后一个数为止。最后所得的那个最大公约数,就是所有这些数的最大公约数。

【C/C++】最大公约数和最小公倍数(辗转相除、更相减损、stein)相关推荐

  1. PYTHON语言编写求最大公约数和最小公倍数的程序(更相减损法)

    #更相减损术求GCD.py x,y=eval(input("请输入一个整数:")) t1,t2=x,y while True:a=abs(x-y)if a==min(x,y):br ...

  2. 最大公约数最小公倍数 辗转相除法 辗转相减法(更相减损法) 穷举法

    最大公约数: 1.辗转相除法 2.辗转相减法(更相减损法) 3.穷举法 最小公倍数:两数的乘积除以最大公约数 方法: 1.判断大小,并使大数赋给a,小数赋给b: 2.辗转相除法:在两数相除余数不为0的 ...

  3. 辗转相处法和更相减损法

    辗转相处法和更相减损法 原理  假设有两个数 a , b (a > b) ,若 c 是两个数的最大公约数,那么a和b一定能表示为c的整数倍,那么用a-b,用得到的结果和a,b中的较大数继续作为下 ...

  4. Python:三种方法计算最大公约数和最小公倍数(欧几里德法、穷举法、stein算法)

    Python:三种方法计算最大公约数和最小公倍数 1.穷举法 2.欧几里德法 3.Stein算法 题目:求取任意两个非负数(至多一个数为0)的最大公约数和最小公倍数: 参考资料:Python解决求最大 ...

  5. 求最大公约数与最小公倍数 (辗转相除法+更相减损法+Stein算法)

    辗转相除法与更相减损法对比: (1)两者都是求最大公因数的方法,计算上辗转相除法以除法为主,更相减损术以减法为主,计算次数上辗转相除法计算次数相对较少,特别当两个数字大小区别较大时计算次数的区别较明显 ...

  6. python求两数最大公因数_『用python求俩个数的最大公约数和最小公倍数』

    python:用递归的方法编写一个函数gys(x,y),计算两个数字的最大公约数. (提示,大的 def gys(x,y): a,b=max(x,y),min(x,y) c=a%b if c==0: ...

  7. 中规中矩的输入两个正整数m和n,求其最大公约数和最小公倍数。

    求取最大公约数有三种方法:## 短除法 把两个数一直除以它们的公约数,取它们的商继续除,直到无约数可除为止.然后把约数全部乘起来,即为最大公约数. 欧几里德算法(辗转相除法) 在两个数中,找出大数.用 ...

  8. 【最大公约数 GCD】 --- 常用四大算法(辗转相除法,穷举法,更相减损法,Stein算法)

    [最大公约数 GCD] --- 常用的四大算法 1. 辗转相除法(又名欧几里德算法) 2. 穷举法(也称枚举法) 3. 更相减损法 (又名辗转相减法) 4. Stein算法 1. 辗转相除法(又名欧几 ...

  9. 五十六、从高中碾转相除法、更相减损术算法谈起

    @Author:Runsen 编程的本质来源于算法,而算法的本质来源于数学,编程只不过将数学题代码化. ---- Runsen 先问你们一个小学问题:如何求两个整数的最大公约数? 曾经见过不少的算法题 ...

  10. 更相减损术程序设计c语言,更相减损术

    本词条缺少概述图,补充相关内容使词条更完整,还能快速升级,赶紧来编辑吧! 更相减损术是出自<九章算术>的一种求最大公约数的算法,它原本是为约分而设计的,但它适用于任何需要求最大公约数的场合 ...

最新文章

  1. java.lang.UnsupportedOperationException: Required method destroyItem was not overridden
  2. 解决Redis报错:MISCONF Redis is configured to save RDB snapshots, but is currently not able to persist
  3. oracle sys改密码,Oracle修改SYS密码
  4. 使用Apache Archiva搭建Maven Repository Server
  5. python 字典处理_python 字典的处理
  6. 华为服务器忘记管理密码怎么修改,忘记云服务器密码怎么修改
  7. 腾讯技术直播间 | 走进小程序云开发
  8. how do you usually upload picture in SCN A workaround for current SCN upload is
  9. aix服务器屏幕显示被锁住了,AIX恢复密码过程总结
  10. r语言kendall协和系数_多变量Kendall协和系数检验.ppt
  11. java语言打印上三角和下三角,进一步得到九九乘法表
  12. 铁甲雄心机器人建造成本_铁甲雄心最强机器人
  13. python 余弦值,Python向量余弦值 Python 求向量的余弦值操作
  14. 动词变名词的变化规则_动词变名词的变化规则例子
  15. 跨考计算机 专硕还是学硕,考研我该如何抉择!专硕学硕不纠结
  16. Python爬虫之爬取豆瓣图书TOP250
  17. CS模式,客户端页面加载
  18. 收缩毛孔全过程,很详细! - 健康程序员,至尚生活!
  19. 臻色调女装官网评价:专业人士展示行业数据
  20. android 9平板电脑截屏,平板电脑怎么截图 平板电脑截图方法【详解】

热门文章

  1. jQuery验证码发送时间秒递减(刷新存储cookie)
  2. ActiveMQ消息队列用法
  3. 关于项目中的封装、重构
  4. [译]GLUT教程 - 笔划字体
  5. 什么是软件测试中的黑天鹅
  6. ASP.NET笔记(二)
  7. Oracle EBS中的“客户”、客户地点、‘订单’之间的关系
  8. [转]IE6对!important支持不彻底
  9. ----vue项目打包之浏览器存在缓存问题----
  10. 第6章 数组、指针与字符串(二)指针与函数