1.辗转相除法
其算法过程为: 前提:设两数为a,b设其中a 做被除数,b做除数,temp为余数
1、大数放a中、小数放b中;
2、求a/b的余数;
3、若temp=0则b为最大公约数;
4、如果temp!=0则把b的值给a、temp的值给a;
5、返回第二步;

函数嵌套调用算法源程序:

int divisor (int a,int b)    /*自定义函数求两数的最大公约数*/
{int  temp;          /*定义整型变量*/if(a<b)             /*通过比较求出两个数中的最大值和最小值*/{temp=a;a=b;b=temp;} /*设置中间变量进行两数交换*/while(b!=0)           /*通过循环求两数的余数,直到余数为0*/{temp=a%b;a=b;              /*变量数值交换*/b=temp;}return(a);            /*返回最大公约数到调用函数处*/
}#include "stdio.h"    /*输入输出类头文件*/
#include<time.h>
int main()
{int a[40],b[40];int t1,Y=0,begintime,endtime;         /*定义整型变量*/for(Y=0;Y<40;Y++){printf("please input two integer number:");                      /*提示输入两个整数*/scanf("%d%d",&a[Y],&b[Y]);                                    /*通过终端输入两个数*/}begintime=clock();for(Y=0;Y<40;Y++){t1=divisor(a[Y],b[Y]);                    /*自定义主调函数*/printf("The higest common divisor is %d\n",t1);                     /*输出最大公约数*/}endtime=clock();printf("\n\nRunnimg Time:%dus\n",1000*(endtime-begintime));
}

函数递归调用算法源程序:

int gcd (int a,int b)
{ if(a%b==0)return b;
elsereturn gcd(b,a%b);}
#include "stdio.h"
#include<time.h>
main()
{int a[40],b[40],t1,Y,begintime,endtime;for(Y=0;Y<40;Y++){printf("please input two integer number:");scanf("%d%d",&a[Y],&b[Y]);}begintime=clock();for(Y=0;Y<40;Y++){t1=gcd(a[Y],b[Y]);printf("The highest common divisor is %d\n",t1);          /*最大公约数*/}endtime=clock();printf("\n\nRunning Time is:%dus\n",1000*(endtime-begintime));
}

3.穷举法
穷举法(也叫枚举法)穷举法求两个正整数的最大公约数的解题步骤:从两个数中较小数开始由大到小列举,直到找到公约数立即中断列举,得到的公约数便是最大公约数 。
对两个正整数a,b如果能在区间[a,0]或[b,0]内能找到一个整数temp能同时被a和b所整除,则temp即为最大公约数。

穷举法源程序:

int divisor (int a,int b) /*自定义函数求两数的最大公约数*/
{int  temp;          /*定义义整型变量*/temp=(a>b)?b:a;    /*采种条件运算表达式求出两个数中的最小值*/while(temp>0)     {if (a%temp==0&&b%temp==0) /*只要找到一个数能同时被a,b所整除,则中止循环*/break;    temp--;      /*如不满足if条件则变量自减,直到能被a,b所整除*/}return (temp); /*返回满足条件的数到主调函数处*/
}
#include "stdio.h"
#include<stdlib.h>
#include<time.h>
int main()
{int a[40],b[40],Y;int t1;int begintime,endtime;for(Y=0;Y<40;Y++){printf("please input two integer number:");scanf("%d%d",&a[Y],&b[Y]);}begintime=clock();for(Y=0;Y<40;Y++){t1=divisor(a[Y],b[Y]);printf("The higest common divisor is %d\n",t1);}endtime=clock();printf("\n\nRunning Time:%dus\n",1000*(endtime-begintime));
}

4.更相减损法
更相减损术,是出自《九章算术》的一种求最大公约数的算法,它原本是为约分而设计的,但它适用于任何需要求最大公约数的场合。《九章算术》是中国古代的数学专著,其中的“更相减损术”可以用来求两个数的最大公约数,即“可半者半之,不可半者,副置分母、子之数,以少减多,更相减损,求其等也。以等数约之。”
翻译成现代语言如下:
第一步:任意给定两个正整数;判断它们是否都是偶数。若是,则用2约简;若不是则执行第二步。
第二步:以较大的数减较小的数,接着把所得的差与较小的数比较,并以大数减小数。继续这个操作,直到所得的减数和差相等为止。
则第一步中约掉的若干个2与第二步中等数的乘积就是所求的最大公约数。
其中所说的“等数”,就是最大公约数。求“等数”的办法是“更相减损”法。所以更相减损法也叫等值算法。

更相减损法源程序:

#include "stdio.h"    /*输入输出类头文件*/
#include<time.h>
#include<math.h>
int gcd(int m,int n)
{int i=0,temp,x;while(m%2==0 && n%2==0)  //判断m和n能被多少个2整除{m/=2;n/=2;i+=1;}if(m<n)     //m保存大的值{temp=m;m=n;n=temp;}x=m-n;while(x){    if(n==(m-n))break;x=m-n;m=(n>x)?n:x;n=(n<x)?n:x;}if(i==0)return n;else return (int )pow(2,i)*n;
}int main()
{int a[40],b[40];int t1,Y=0,begintime,endtime;         /*定义整型变量*/for(Y=0;Y<1;Y++){printf("please input two integer number:");                       /*提示输入两个整数*/scanf("%d%d",&a[Y],&b[Y]);                                    /*通过终端输入两个数*/}begintime=clock();for(Y=0;Y<1;Y++){t1=gcd(a[Y],b[Y]);                    /*自定义主调函数*/printf("The higest common divisor is %d\n",t1);                      /*输出最大公约数*/}endtime=clock();printf("\n\nRunnimg Time:%dus\n",1000*(endtime-begintime));
}

5.stein算法
Stein算法由J. Stein 1961年提出,这个方法也是计算两个数的最大公约数。来研究一下最大公约数的性质,发现有 gcd( kx,ky ) = kgcd( x,y ) 这么一个非常好的性质。试取 k=2,则有 gcd( 2x,2y ) = 2 * gcd( x,y )。很快联想到将两个偶数化小的方法。那么一奇一个偶以及两个奇数的情况如何化小呢?
先来看看一奇一偶的情况: 设有2x和y两个数,其中y为奇数。因为y的所有约数都是奇数,所以 a = gcd( 2x,y ) 是奇数。根据2x是个偶数不难联想到,a应该是x的约数。我们来证明一下:(2x)%a=0,设2x=n
a,因为a是奇数,2x是偶数,则必有n是偶数。又因为 x=(n/2)*a,所以 x%a=0,即a是x的约数。因为a也是y的约数,所以a是x和y的公约数,有 gcd( 2x,y ) <= gcd( x,y )。因为gcd( x,y )明显是2x和y的公约数,又有gcd( x,y ) <= gcd( 2x,y ),所以 gcd( 2x,y ) = gcd( x,y )。至此,我们得出了一奇一偶时化小的方法。
再来看看两个奇数的情况:设有两个奇数x和y,不妨设x>y,注意到x+y和x-y是两个偶数,则有 gcd( x+y,x-y ) = 2 * gcd( (x+y)/2,(x-y)/2 ),那么 gcd( x,y ) 与 gcd( x+y,x-y ) 以及 gcd( (x+y)/2,(x-y)/2 ) 之间是不是有某种联系呢?为了方便设 m=(x+y)/2 ,n=(x-y)/2 ,容易发现 m+n=x ,m-n=y 。设 a = gcd( m,n ),则 m%a=0,n%a=0 ,所以 (m+n)%a=0,(m-n)%a=0 ,即 x%a=0 ,y%a=0 ,所以a是x和y的公约数,有 gcd( m,n )<= gcd(x,y)。再设 b = gcd( x,y )肯定为奇数,则 x%b=0,y%b=0 ,所以 (x+y)%b=0 ,(x-y)%b=0 ,又因为x+y和x-y都是偶数,跟前面一奇一偶时证明a是x的约数的方法相同,有 ((x+y)/2)%b=0,((x-y)/2)%b=0 ,即 m%b=0 ,n%b=0 ,所以b是m和n的公约数,有 gcd( x,y ) <= gcd( m,n )。所以 gcd( x,y ) = gcd( m,n ) = gcd( (x+y)/2,(x-y)/2 )。
整理一下,对两个正整数 x>y :
1.均为偶数 gcd( x,y ) =2gcd( x/2,y/2 );
2.均为奇数 gcd( x,y ) = gcd( (x+y)/2,(x-y)/2 );
2.x奇y偶 gcd( x,y ) = gcd( x,y/2 );
3.x偶y奇 gcd( x,y ) = gcd( x/2,y ) 或 gcd( x,y )=gcd( y,x/2 );
现在已经有了递归式,还需要再找出一个退化情况。注意到 gcd( x,x ) = x ,就用这个。

函数非递归调用算法源程序:

int Stein( unsigned int x, unsigned int y )
/* return the greatest common divisor of x and y */
{int factor = 0;int temp;if ( x < y ){temp = x;x = y;y = temp;}if ( 0 == y ){return 0;}while ( x != y ){if ( x & 0x1 )//判断x是否为奇数{                                         /* when x is odd */if ( y & 0x1 )//判断y是否为奇数{                                    /* when x and y are both odd */y = ( x - y ) >> 1;//相当于(x-y)/2x -= y;}else//x是奇数y是偶数{                               /* when x is odd and y is even */y >>= 1;}}else{                                     /* when x is even */if ( y & 0x1 )//x是偶数y是奇数{                               /* when x is even and y is odd */x >>= 1;//相当于x=x>>1;或者x=x/2;if ( x < y ){temp = x;x = y;y = temp;}}else//x,y均是偶数{/* when x and y are both even */x >>= 1;y >>= 1;++factor;}}}return ( x << factor );
}
#include "stdio.h"    /*输入输出类头文件*/
#include<time.h>
int main()
{int a[40],b[40];int t1,Y=0,begintime,endtime;         /*定义整型变量*/for(Y=0;Y<40;Y++){printf("please input two integer number:");                      /*提示输入两个整数*/scanf("%d%d",&a[Y],&b[Y]);                                    /*通过终端输入两个数*/}begintime=clock();for(Y=0;Y<40;Y++){t1=Stein(a[Y],b[Y]);                    /*自定义主调函数*/printf("The higest common divisor is %d\n",t1);                   /*输出最大公约数*/}endtime=clock();printf("\n\nRunnimg Time:%dus\n",1000*(endtime-begintime));
}

函数递归调用算法源程序:

int gcd(int u,int v)
{if (u == 0) return v;if (v == 0) return u;// look for factors of 2if (~u & 1) // u is even{if (v & 1) // v is oddreturn gcd(u >> 1, v);else // both u and v are evenreturn gcd(u >> 1, v >> 1) << 1;}if (~v & 1) // u is odd, v is evenreturn gcd(u, v >> 1);// reduce larger argumentif (u > v)return gcd((u - v) >> 1, v);return gcd((v - u) >> 1, u);
}
#include "stdio.h"    /*输入输出类头文件*/
#include<time.h>
int main()
{int a[40],b[40];int t1,Y=0,begintime,endtime;         /*定义整型变量*/for(Y=0;Y<40;Y++){printf("please input two integer number:");                      /*提示输入两个整数*/scanf("%d%d",&a[Y],&b[Y]);                                    /*通过终端输入两个数*/}begintime=clock();for(Y=0;Y<40;Y++){t1=gcd(a[Y],b[Y]);                    /*自定义主调函数*/printf("The higest common divisor is %d\n",t1);                     /*输出最大公约数*/}endtime=clock();printf("\n\nRunnimg Time:%dus\n",1000*(endtime-begintime));
}

总结:程序中没有读写文件的功能,当需要计算大量的数据时,需要人为输入,较为繁琐,需要计算多少组数据时,需要将代码中的for循环修改即可。这几个程序均可以计算数据的最大公约数,还有计算程序运行时间的功能,并且输出运行时间,其中辗转相除法最为快捷,穷举法最为缓慢。需要特别注意的是stein算法中涉及到了一些不常见的运算符,大家在用的时候,希望能明白这些运算符的意义,并学以致用。虽然有些许的问题,但是我会逐步改进的,加油。

几种常见的算法求最大公约数(C语言)相关推荐

  1. 四种算法求最大公约数

    四种算法求最大公约数(C++) 一. 实验目的 明确算法的概念和特点. 通过对问题的分析,设计合理的算法解决问题: 二. 实验内容 运行最大公约数的常用算法,并进行程序的调式与测试,要求程序设计风格良 ...

  2. 8种常见机器学习算法比较

    8种常见机器学习算法比较 2016-08-04 17:46 转载 陈圳 0条评论 雷锋网(搜索"雷锋网"公众号关注)按:本文转自刘志伟责编,在机器学习中选择一个恰当的算法十分重要, ...

  3. c语言怎样求最大公约数,c语言求最大公约数

    求差判定法. 如果两个数相差不大,可以用大数减去小数,所得的差与小数的最大公约数就是原来两个数的最大公约数.例如:求78和60的最大公约数.78-60=18,18和60的最大公约数是6,所以78和60 ...

  4. 欧几里德算法求最大公约数

    在求两个数的最大公约数方法中, 辗转相除法是比较快的一种方法. 也就是著名的欧几里德方法. View Code int Gcd(int a, int b){return b==0?a:gcd(b, a ...

  5. Java几种常见排序算法与代码实现

    前言: 排序算法也算是每年校招.春招.社招都会问到的问题,虽然每次复习了就忘,但是也可以隔一段时间又拿出来看看. 其中,排序方式指,内部还是外部排序.只需要内部内存就可以的称为内部排序,数据量太大需要 ...

  6. C语言用for循环求最大公约数,C语言循环结构 -C语言求最大公约数

    这是一个C语言 while 循环示例:求正整数 m 和 n 的最大公约数. 问题分析 输入:两个正整数. 输出:一个正整数(最大公约数). 最大公约数(gcd)是指几个数共有的因数之中最大的一个数,比 ...

  7. 用函数求最大公约数c语言,C语言求最大公约数公式分享

    从键盘输入两个正整数 a 和 b,求其最大公约数和最小公倍数. 算法思想 利用格式输入语句将输入的两个数分别赋给 a 和 b,然后判断 a 和 b 的关系,如果 a 小于 b,则利用中间变量 t 将其 ...

  8. 用c语言怎么求最大公约数,c语言求最大公约数

    c语言求最大公约数[编辑] 概述 c语言是一种计算机编程语言,该语言的优势在于任何环境都能运行并能达到简易的方式编译.处理低级存储器和产生少量的机器码等效果. c语言是一种计算机编程语言,该语言的优势 ...

  9. 求最大公约数c语言代码_辗转相除求最大公约数原理

    辗转相除法代码 代码并不难,很多人都会写. public static int f(int a, int b){ while(b != 0){ int temp = b; b = a % b; a = ...

最新文章

  1. 【IEEE】2020 年AI's 10 To Watch名单新鲜出炉!MIT韩松、方飞、张含望等华人入选!...
  2. 比特币现金是银行的一种补充
  3. 第一次使用JMETER:JMETER hello word
  4. pythonscatter简书_python plotly 使用教程
  5. python 会计专用格式_python-2.7 – 如何使用xlsxwriter将格式应用为“文本”和“会计”...
  6. Flutter Mac下环境配置
  7. linux awk 教程,linux awk使用
  8. 由ExecutorService及Callable実现有返回值的线程
  9. 显示器说:偶好惨啊,每天给人看。
  10. Log4J发日志邮件给多个接收者及标题、正文乱码问题
  11. 异步通信在生活中的例子_通信技术在日常生活中的作用
  12. Python计算贝塔系数和夏普比率
  13. Layui 后台管理模板 【Y-Admin】
  14. oracle中常使用到的函数,Oracle经常使用到的函数
  15. 购买学生服务器、备案域名、搭建博客菜鸟级教程
  16. 硬路由、软路由、主路由、旁路由对比分析
  17. oier必备的博客和OJ
  18. 【IT职场】如何成为T型甚至A型人物。
  19. 知乎广告效果怎么样?有哪些优势呢?
  20. 基于javaagent-ByteBuddy监控方法执行耗时

热门文章

  1. C#事务处理(三)之Transactions事务
  2. 技术部负责人的爱恨情仇
  3. 【程序人生】IT界含金量高的证书
  4. 科研级试剂材料磷脂聚乙二醇马来酰亚胺 DSPE-PEG-MAL----为华生物
  5. 【Android开发】App消息中心构建
  6. 读《MacTalk#183;人生元编程》及Mac经常使用软件
  7. 世界五百强背景,为啥到了保险行业就成了「小公司」?
  8. 编译原理学习 一 什么是编译程序
  9. Python实现文件夹复制操作
  10. 网络原理(Java网络编程)