扩展欧几里德 POJ 1061

时间:2023-01-22 13:45:08

欧几里德的是来求最大公约数的,扩展欧几里德,基于欧几里德实现了一种扩展,是用来在已知a, b求解一组x,y使得ax+by = Gcd(a, b) =d(解一定存在,根据数论中的相关定理,证明是用裴蜀定理),关于欧几里德的证明请看上篇。

基本算法:基本算法:对于不完全为 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. ab!=0 时

设 ax1+by1=gcd(a,b);

  bx2+(a mod b)y2=gcd(b,a mod b);

  根据朴素的欧几里德原理有 gcd(a,b)=gcd(b,a mod b)

  则:ax1+by1=bx2+(a mod b)y2;

  即:ax1+by1=bx2+(a-(a/b)*b)y2=ay2+bx2-(a/b)*by2;

  根据恒等定理得:x1=y2; y1=x2-(a/b)*y2;(这个式子是递归的另外一部分,很重要的一步)

  这样我们就得到了求解 x1,y1 的方法:x1,y1 的值基于 x2,y2.

   上面的思想是以递归定义的,因为 gcd 不断的递归求解一定会有个时候 b=0,所以递归可以结束。

所以求代码可以如下

int exgcd(int a, int b, int &x, int &y)
{
if (b == )
{
x = ;
y = ;
return a; // a,b的最大公约数的求法(gcd)
}
int r = exgcd(b, a % b, x, y);
int t = x;
x = y;
y = t - a / b * y;
return r;//最大公约数
}

POJ 1061青蛙的约会这个题是求不定方程的解的,有题意可列方程(n-m)*s + k * L = x - y; 、

令a = n - m; b = L; c = x - y;

这个式子这时就是a * s + b * k = c;典型的不定方程

求解过程:

1. 首先计算gcd(a, b); 如果c不能整除gcd(a, b)那么就是没有解的,因为gcd(a, b)是a*s+b*k的线性组合的最小正整数, x,y∈z; 否则,方程两边同时除以gcd(a, b)得到新的方程a' * s + b' * k = c'; 这时候a', b'是互质的,所以gcd(a', b') = 1。

2. 利用上面所说的欧几里德算法求出方程a' * s + b' * k = 1的一组整数解x0,y0, 那么c' * x0, c' * y0就是方程a' * s + b' * k = c' 的一组整数解

3. 求方程组的通解,这时候就需要一些数论中的证明(a' * s + b' * k = c' 可以写成 a' * (s + t * b') + b' * (k - t * a') = c', t为整数, 所以通解s=s + t * b', k= k - t * a')

通解为:s=s + t * b', k= k - t * a'

所以它的最小正整数解为 (t % b' + b') % b';

代码如下:

#include <cstdio>
#include <iostream> typedef long long LL; int gcd(LL a, LL b)
{
return b == ? a : gcd(b, a % b);
}
void exgcd(LL a, LL b, LL &x, LL &y)
{
if (b == )
{
x = ;
y = ;
return;
}
exgcd(b, a % b, x, y);
LL t = x;
x = y;
y = t - (a / b) * y;
}
int main()
{ LL x, y, n, m, L;
while (~scanf("%I64d %I64d %I64d %I64d %I64d", &x, &y, &m, &n, &L))
{
LL a, b, c, r, k1, k2, GCD;
a = n - m;
b = L;
c = x - y;
GCD = gcd(a, b);
if (c % GCD != )
{
puts("Impossible");
}
else
{
a /= GCD;
b /= GCD;
c /= GCD;
exgcd(a, b, k1, k2);
k1 *= c;//为其中一个解
k1 = (k1 % b + b) % b;//最小正整数解
printf("%I64d\n", k1);
}
}
return ;
}
														
		

扩展欧几里德 POJ 1061的更多相关文章

  1. 数学&num;扩展欧几里德 POJ 1061&amp&semi;2115&amp&semi;2891

    寒假做的题了,先贴那时写的代码. POJ 1061 #include<iostream> #include<cstdio> typedef long long LL; usin ...

  2. poj 1061 青蛙约会(扩展欧几里德)

    题目链接: http://poj.org/problem?id=1061 题目大意: 中文题目,题意一目了然,就是数据范围大的出奇. 解题思路: 假设两只青蛙都跳了T次,可以列出来不定方程:p*l + ...

  3. ACM&colon; POJ 1061 青蛙的约会 -数论专题-扩展欧几里德

    POJ 1061 青蛙的约会 Time Limit:1000MS     Memory Limit:10000KB     64bit IO Format:%lld & %llu  Descr ...

  4. POJ 1061 青蛙的约会(扩展欧几里德)

    点我看题目 题意 : 中文题不详述. 思路 : 设经过s步后两青蛙相遇,则必满足(x+m*s)-(y+n*s) = K*L(k = 0,1,2....) 变形得:(n-m)*s+K*L = x-y ; ...

  5. POJ 1061 青蛙的约会(扩展欧几里德算法)

    题意:两只青蛙在同一个纬度上跳跃,给定每个青蛙的开始坐标和每秒跳几个单位,纬度长为L,求它们相遇的最短时间. 析:开始,一看只有一组数据,就想模拟一下,觉得应该不会超时,但是不幸的是TLE了,我知道这 ...

  6. poj 1061 青蛙的约会 &lpar;扩展欧几里得模板&rpar;

    青蛙的约会 Time Limit:1000MS     Memory Limit:10000KB     64bit IO Format:%I64d & %I64u Submit Status ...

  7. POJ 1061 青蛙的约会&lpar;扩展GCD求模线性方程)

    题目地址:POJ 1061 扩展GCD好难懂.. 看了半天.最终把证明什么的都看明确了. .推荐一篇博客吧(戳这里),讲的真心不错.. 直接上代码: #include <iostream> ...

  8. POJ 2142 The Balance【扩展欧几里德】

    题意:有两种类型的砝码,每种的砝码质量a和b给你,现在要求称出质量为c的物品,要求a的数量x和b的数量y最小,以及x+y的值最小. 用扩展欧几里德求ax+by=c,求出ax+by=1的一组通解,求出当 ...

  9. POJ 2891 扩展欧几里德

    这个题乍一看跟剩余定理似的,但是它不满足两两互素的条件,所以不能用剩余定理,也是给了一组同余方程,找出一个X满足这些方程,如果找不到的话就输出-1 因为它不满足互素的条件,所以两个两个的合并,最后合成 ...

随机推荐

  1. python求数字位数的方法

    第一种:利用str()函数将数字转化成字符串,再利用len()函数判断位长. a=Int(raw_input("the number you want type in:") b=l ...

  2. 代理延迟加载中proxy和弄no-proxy区别

    Child   <-   many-to-one   ->Parent         class   Child   {         private   Parent   paren ...

  3. CURL

    基本语法: function curl($url){ $ch=curl_init();  //初始化 curl_setopt($ch, CURLOPT_URL, $url); //核心 curl_se ...

  4. HDU 4831 Scenic Popularity

    Scenic Popularity Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others ...

  5. BJFU 1034

    描述 对于任意的两个非负整数a,b(0<=a,b<10000),请计算a^b各位数字的和的各位数字的和-- 输入 输入两个非负整数a,b(0<=a,b<10000),注意哦,输 ...

  6. ios - cordova&lpar;phoneGap&rpar;

    安装教程 下载 node.js. http://nodejs.org/ 下载后,直接安装就可以了. 安装 Cordova工具, $ sudo npm install -g cordova 创建APP: ...

  7. PHP之路——Redis安装

    windows: redis下载链接:https://github.com/ServiceStack/redis-windows 然后编辑redis.windows.conf文件,我看网上有的教程说编 ...

  8. ejs 基本语法

    1.基本语法.<% code %>    无缓冲的条件语句元素.<%= code %>    转义HTML,该code并且会打印出来.<%- code %>     ...

  9. React学习笔记(一)- 环境搭建

    最近在学习react相关的知识,刚刚起步,一路遇坑不断.自己做个笔记,方便日后总结,也供相同趣味的小伙伴一起交流探讨. 学习时主要参考官网的教程:https://facebook.github.io/ ...

  10. IdentityServer4【QuickStart】之利用OpenID Connect添加用户认证

    利用OpenID Connect添加用户认证 利用OpenID Connect添加用户认证 在这个示例中我们想要通过OpenID Connect协议将交互用户添加到我们的IdentityServer上 ...