NOIp提高组 2012 同余方程————扩展欧几里得定理

题解:本题主要考查扩展欧几里得定理。
简要题意:求 a x ≡ 1 ( m o d b ) a x \equiv 1 \pmod {b} ax1(modb)最小正整数解
1.扩展欧几里得定理: a x ≡ 1 ( m o d b ) a x \equiv 1 \pmod {b} ax1(modb),等价与 a ∗ x + m ∗ y = 1 a*x+m*y=1 ax+my=1
因为裴蜀定理 a x + b y = z , 则 g c d ( a , b ) ∣ z ax+by=z,则gcd(a,b)|z ax+by=z,gcd(a,b)z g c d ( a , b ) = 1 ; gcd(a,b)=1; gcd(a,b)=1;
又因为 g c d ( a , b ) = g c d ( b , a m o d    b ) gcd(a,b)=gcd(b,a\mod b) gcd(a,b)=gcd(b,amodb)所以 b ∗ x 1 + ( a m o d    b ) ∗ y 1 = g c d ; b*x_1+(a\mod b)*y_1=gcd; bx1+(amodb)y1=gcd;
又因为 a m o d    b = a − ( a / b ) ∗ b ; a\mod b=a-(a/b)*b; amodb=a(a/b)b;
所以 b ∗ x 1 + ( a − ( a / b ) ∗ b ) ∗ y 1 b*x1 + (a-(a/b)*b)*y1 bx1+(a(a/b)b)y1
= b ∗ x 1 + a ∗ y 1 – ( a / b ) ∗ b ∗ y 1 = b*x1+a*y1–(a/b)*b*y1 =bx1+ay1(a/b)by1
= a ∗ y 1 + b ∗ ( x 1 – a / b ∗ y 1 ) = g c d = a*y_1 + b*(x1 – a/b*y1) = gcd =ay1+b(x1a/by1)=gcd
所以 x = y 1 , y = x 1 – a / b ∗ y 1 ; x=y_1,y=x1 – a/b*y1; x=y1,y=x1a/by1;
因此到最后,如果 x x x太小就不断加 b b b直到大于等于 0 0 0,太大则一直减 b b b,直到最小正整数解。直接求模实现更快。
(其实暴力也可,亲测70分QwQ)
代码如下:

#include<iostream>
#include<cstdio>
using namespace std;
long long a,b,x,xx,y;
void exgcd(long long a,long long b)
{
	if(b==0)
	{
		x=1;y=0;
		return ;
	}
	exgcd(b,a%b);
	xx=x;x=y;y=xx-(a/b)*y;
	return ;
}
int main()
{
	ios::sync_with_stdio(false);
	cin>>a>>b;
	exgcd(a,b);
	cout<<(x+b)%b;
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值