辗转相除法与更相减损法对比:

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

(2)从结果体现形式来看,辗转相除法体现结果是以相除余数为0则得到,而更相减损术则以减数与差相等而得到。

更相损减法在两数相差较大时,时间复杂度容易退化成O(N),而辗转相除法可以稳定在O(logN)。但辗转相除法需要试商,这就使得在某些情况下,使用更相损减法比使用辗转相除法更加简单。

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

最大公约数

方法一:(一行代码简洁明了)

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

方法二(递归转为循环):

int gcd(int a, int b)
{
while(b != 0)
{
int r = b;b = a % b;a = r;}
return a;
}

最小公倍数:

a*b/GCD(a,b);

a*b/gcd(a,b);

求N个数的最大公约数:

#include <stdio.h>
#include <stdlib.h>int gcd(int a, int b)
{if(a < b) a = a^b, b = b^a, a = a^b;int c = a%b;while(a%b != 0){a = b, b = c, c = a % b;}return b;
}int main()
{int num[20], n;scanf("%d",&n);for(int i = 1; i <= n; i++)scanf("%d",&num[i]);int ans = num[1];for(i = 2; i <= n; i++)ans = gcd(ans, num[i]);printf("%d",ans);return 0;}

同理也可求N个数的最小公倍数,学会举一反三.

更相减损法:

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

stein算法(重点):

欧几里德算法是计算两个数最大公约数的传统算法,无论从理论还是从实际效率上都是很好的。但是却有一个致命的缺陷,这个缺陷在素数比较小的时候一般是感觉

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

Stein算法很好的解决了欧几里德算法中的这个缺陷,Stein算法只有整数的移位和加减法。下面就来说一下Stein算法的原理:

  • 若a和b都是偶数,则记录下公约数2,然后都除2(即右移1位);
  • 若其中一个数是偶数,则偶数除2,因为此时2不可能是这两个数的公约数了
  • 若两个都是奇数,则a = |a-b|,b = min(a,b),因为若d是a和b的公约数,那么d也是|a-b|和min(a,b)的公约数。
  • 代码实现:

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

    递归转循环:

  • 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;
    }

    想要深入了解的话可以看一下大佬的博客,里面讲的挺详细的(附链接):

  • https://blog.csdn.net/Holmofy/article/details/76401074#%E4%BB%A3%E7%A0%81%E5%AE%9E%E7%8E%B0-1

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

  1. 求最大公约数和最小公倍数(更相减损法/辗转相除法)

    目录 一.最大公约数 1.1 更相减损法 1.2 辗转相除法 二.最小公倍数 2.1 最小公倍数=两数相乘/最大公约数 2.2 用较小数的倍数除以较大数 一.最大公约数 1.1 更相减损法 原理如下图 ...

  2. 辗转相除法+更相减损法求最大公约数

    怎么求两个数的最大公约数呢? 简单的想法就是直接暴力枚举,试出最大公约数 #暴力枚举 #暴力枚举 def GCD(numberA,numberB):gcd=1for i in range(2,max( ...

  3. 【求最大公约数详解】更相减损术和辗转相除法

    更相减损术 介绍 ​   更相减损术是出自<九章算术>的一种求最大公约数的算法,它原本是为约分而设计的,但它适用于任何需要求最大公约数的场合 步骤 任意给定两个正整数:判断它们是否都是偶数 ...

  4. 【C语言】辗转相除法+更相减损术+秦九韶算法

    一.辗转相除法 1.简介 辗转相除法又叫欧几里得算法. 假如需要求 1997 和 615 两个正整数的最大公约数,用欧几里得算法,是这样进行的: 1997 / 615 = 3 (余 152) 615 ...

  5. 【原创】更相减损术 stein算法 欧几里得算法 拓展欧几里得算法 扩展欧几里得算法 逆元的计算与筛法 解模线性方程

    欧几里得 说在前面 数论学复习 Part 6. 然后再来一章CRT和组合数,就飞往概率,以此为跳板去向DP. 计划很美啊你. P.S. 这么说来拉格朗日插值可以说是数论学复习的Part 0了啊. 有一 ...

  6. 辗转相除法、更相减损法、Stein算法

    最大公约数和最小公倍数求解,常用的方法是短除法进行因式分解,然后最大公约数是所有公共因子的乘积,最小公倍数是所有因子的乘积. 本质上求最小公倍数就是求最大公倍数:x=m*a, y=m*b:m是最大公约 ...

  7. C:求两个数的最大公约数详解(硬核算法,辗转相除法,更相减损法)

    最大公因数,也称最大公约数.最大公因子. 定义: 指两个或多个整数共有约数中最大的一个. a,b的最大公约数 记为(a,b),同样的,a,b,c的最大公约数记为(a,b,c),多个整数的最大公约数也有 ...

  8. C++ 求最大公约数 更相减损法 欧几里得算法 暴力穷举法

    两个数的最大公约数是指能同时被他们整除的最大正整数. 两个数的最大公约数等于它们中 较小的数 和 两数之差 的最大公约数. 252和105的最大公约数是21(252 = 21 × 12:105 = 2 ...

  9. C语言复习---获取最大公约数(辗转相除法和更相减损法)

    源自:百度百科 辗转相除法 辗转相除法:辗转相除法是求两个自然数的最大公约数的一种方法,也叫欧几里德算法. 例如,求(319,377): ∵ 319÷377=0(余319) ∴(319,377)=(3 ...

最新文章

  1. Oracle ASM 详解 收藏
  2. sublime配置运行python文件的快捷键
  3. 【S操作】简单粗暴自动化免费文档存储备份方案
  4. Python—— *与** 参数说明
  5. html分步调试,一般纯HTML网页的JavaScript的单步执行与调试(以VS2005)
  6. xtrabackup mysql8.0_Percona XtraBackup 8.0, 安装与测试
  7. 深度学习:卷积神经网络CNN变体
  8. linux系统维护诸多定时器,linux定时器总结
  9. Linux LCD 驱动调色板原理
  10. 新概念英语(第一册)复习(原文及全文翻译)——Lesson 111 - Lesson 130
  11. 微信二次分享签名错误php,微信二次分享报错invalid signature问题及解决方法
  12. 风险收益导论-简单收益率与连续复利收益率
  13. html只选择年份,原生jQuery实现只显示年份下拉框
  14. 《Effective C++》学习笔记(条款25:考虑写出一个不抛异常的swap函数)
  15. Ubuntu16.04下的主题美化
  16. 微信小程序引入iconfont单色图标实例
  17. 计算机网络 互联网模拟实验
  18. shell小技巧(一百三十三)n个人报数出局游戏
  19. 2018提高组模拟13
  20. 机械硬盘smartID05 警告怎么办?

热门文章

  1. css3宽度变大动画_HTML5如何实现动画效果
  2. 【统计模型】大学生恋爱数据分析报告
  3. 码农你看懂了,就发财了
  4. Python方法与函数的区别
  5. Netty对象池 Recycler
  6. PLSQL Developer备份恢复oracle数据
  7. maven插件之Dependency:analyze
  8. 统计语言模型:Bi-gram
  9. 关于node环境下用npm下载node-sass错误的解决方法
  10. c语言学生成绩管理实验报告,学生成绩管理系统c语言实验报告