关闭

扩展欧几里得算法

标签: 数论扩展欧几里德算法exgcd
522人阅读 评论(2) 收藏 举报
分类:
扩展欧几里得算法用于:
1.求不定方程
2.求解模的逆元

3.求解同余方程

/*
 * 扩展欧几里得算法(extended Euclidean algorithm)
 * 扩展欧几里德算法是用来在已知a, b求解一组x,y,使它们满足贝祖等式:
 * ax+by = gcd(a, b) = d(解一定存在,根据数论中的相关定理)。
 * 扩展欧几里德常用在求解模线性方程及方程组中。
 *
 */

#include <stdio.h>

// 递归法实现扩展欧几里德算法
long exgcd1(long a, long b, long *x, long *y)
{
    if(b==0) {
        *x=1;
        *y=0;
        return a;
    }

    long r = exgcd1(b, a%b, x, y);
    long t = *x;
    *x = *y;
    *y = t - a / b * *y;

    return r;
}

// 递推法实现扩展欧几里德算法(正解)
long exgcd2(long a, long b, long *x, long *y)
{
    long x0=1, y0=0, x1=0, y1=1;
    long r, q;
    *x=0;
    *y=1;

    r = a % b;
    q = (a - r) / b;
    while(r)
    {
        *x = x0 - q * x1;
        *y = y0 - q * y1;
        x0 = x1;
        y0 = y1;
        x1 = *x;
        y1 = *y;

        a = b;
        b = r;
        r = a % b;
        q = (a - r) / b;
    }
    return b;
}

int main(void)
{
    long x, y;

    printf("a=%d, b=%d, x=%ld, y=%ld exgcd=%ld\n", 42, 70, x, y, exgcd1(42, 70, &x, &y));

    printf("a=%d, b=%d, x=%ld, y=%ld exgcd=%ld\n", 42, 70, x, y, exgcd2(42, 70, &x, &y));

    return 0;
}


关键代码(正解):

// 递推法实现扩展欧几里德算法(正解)
long exgcd2(long a, long b, long *x, long *y)
{
    long x0=1, y0=0, x1=0, y1=1;
    long r, q;
    *x=0;
    *y=1;

    r = a % b;
    q = (a - r) / b;
    while(r)
    {
        *x = x0 - q * x1;
        *y = y0 - q * y1;
        x0 = x1;
        y0 = y1;
        x1 = *x;
        y1 = *y;

        a = b;
        b = r;
        r = a % b;
        q = (a - r) / b;
    }
    return b;
}



1
0
查看评论
发表评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场

扩展欧几里得算法及其应用

扩展欧几里德算法 基本算法:对于不完全为 0 的非负整数 a,b,gcd(a,b)表示 a,b 的最大公约数,必然存在整数对 x,y ,使得 gcd(a,b)=ax+by。 证明:设 a>b。   1,显然当 b=0,gcd(a,b)=a。此时 x=1,y=0;   2...
  • rebelqsp
  • rebelqsp
  • 2014-02-24 20:03
  • 2129

扩展欧几里德算法模版题(求逆元+分析+题目)HDU1576 A/B

首先给大家普及一下什么是扩展欧几里德算法,它是由欧几里德算法演变的,即我们常说的辗转相除法。 代码如下: int gcd(int a,int b){     return b?gcd(b,a%b):a; } 那...
  • Singular__point
  • Singular__point
  • 2016-11-18 16:56
  • 1191

扩展欧几里德算法Java实现和青蛙相遇

问题衔接: http://poj.org/problem?id=1061 Description 两只青蛙在网上相识了,它们聊得很开心,于是觉得很有必要见一面。它们很高兴地发现它们住在同一条纬度线上,于是它们约定各自朝西跳,直到碰面为止。可是它们出发之前忘记了一件很重要的事情,既没有问清楚对方...
  • zs064811
  • zs064811
  • 2017-02-12 17:59
  • 959

ACM_扩展欧几里得算法

我们先来回顾一下欧几里得算法,欧几里得算法是用于求两个数的最大公约数:其核心为一句 Gcd(a, b) = Gcd(b, a%b) (Gcd表示两个数的最大公约数),直到a%b == 0时,可得到Gcd(a,b)的具体值。 我们再来看一下扩展欧几里得算法在乘法逆元上的运用,先来介绍一下乘法逆元,可能...
  • RaAlGhul
  • RaAlGhul
  • 2016-05-23 18:59
  • 572

【专题】欧几里得算法、扩展欧几里得、乘法逆元

1.欧几里得 用途 最大公因数和最小公倍数 定理:  gcd(a,b)=gcd(b,a%b)gcd(a,b)=gcd(b,a\%b)   证明: 我们令c=gcd(a,b)c=gcd(a,b) 令a=n∗ca=n*c , b=m∗cb=m*c a%b=a−k∗b=(n−m∗k...
  • mmy1996
  • mmy1996
  • 2016-10-31 23:29
  • 861

扩展欧几里德算法(附证明)

扩展欧几里德算法(附证明) 扩展欧几里得算法在acm-icpc中是常用算法,主要用于在已知a,b的情况下求解一组x,y,使它们满足贝祖等式: ax+by=gcd(a,b)=dax+by = gcd(a, b) =d.
  • lincifer
  • lincifer
  • 2015-10-24 23:45
  • 4313

扩展欧几里德算法详解以及乘法逆元

转载网址:http://blog.csdn.net/zhjchengfeng5/article/details/7786595 有些地方看不懂,但觉得写的很棒,先转载下来,以后慢慢研究…… 扩展欧几里德算法:     谁是欧几里德?自己百度去 ...
  • Stray_Lambs
  • Stray_Lambs
  • 2016-08-05 22:26
  • 6326

欧几里得扩展算法详解及POJ1061

最初是在PKU的acm上刷题,刚接触1061青蛙的约会这道题的时候写了个简单暴力的方法,在一定范围内感觉挺对的,但是提交后WA了,于是在一起K题的战友那里第一次听说了这个算法——欧几里得扩展算法。费了很大的劲之后,终于有些了解这个算法了,在这记录下。 所谓扩展欧几里得算法就是给定一组a,b,求aX+...
  • silent_strings
  • silent_strings
  • 2013-07-04 13:37
  • 1755

欧几里得 & 拓展欧几里得算法 讲解 (Euclid & Extend- Euclid Algorithm)

欧几里得& 拓展欧几里得(Euclid & Extend-Euclid) 欧几里得算法(Euclid) 背景: 欧几里德算法又称辗转相除法,用于计算两个正整数a,b的最大公约数。 ——百度百科 代码: 递推的代码是相当的简洁: …. 分析: 方法说了是辗转相除法,自然没有什么好介绍...
  • ACMore_Xiong
  • ACMore_Xiong
  • 2015-08-16 02:10
  • 8078

对于拓展欧几里德算法的理解

对于不完全为 0 的非负整数 a,b,gcd(a,b)表示 a,b 的最大公约数,必然存在整 数对 x,y ,使得 gcd(a,b)=ax+by。 c++语言的实现: int exgcd(ll a,ll b,ll &x,ll &am...
  • yeweiyang16
  • yeweiyang16
  • 2015-08-02 08:15
  • 475
    个人资料
    • 访问:909490次
    • 积分:20720
    • 等级:
    • 排名:第452名
    • 原创:1086篇
    • 转载:87篇
    • 译文:0篇
    • 评论:403条
    文章分类
    博客专栏
    最新评论