扩展欧几里德算法——求最小整数解
这是一个数学推导!!!
首先我们已经知道了,如何通过扩展欧几里德算法,求出方程的其中一组解了
那么就可以继续往下看
给出两个方程
ax1+by1=gcd(a,b)
ax2+by2=gcd(a,b)
所以可以推出
ax1+by1=ax2+by2
a(x1-x2)=b(y2-y1)
然后我们知道gcd(a,b)为a,b的最大公因数,所以我们将 A=a/gcd(a,b),B=b/gcd(a,b),接着往下推出
A(x1-x2)=B(y2-y1)
现在A和B两个已经是互素了,所以又可以接着推出
(这个地方要好好理解,重点!)
A*(n*B)=B*(n*A)
(x1-x2)=n*B
(y2-y1)=n*A
这里我们从x入手
(x1-x2)=n*B
x1=x2+n*B
由此,我们推出了x解的通解公式 x=x0+n*B
同理,我们推出了y解的通解公式 y=y0-m*A
那么我们如果要求 x 的最小整数解,也就是 x0, 就是 x0=x%B
如果我们要求的是 ax+by=c,还得先转化 x=x*c/gcd(a,b).
然后套入我们的公式
B=b/gcd(a,b)
x0=x%(b/gcd(a,b))
嗯,到此结束,下面给下实现代码
#include <bits/stdc++.h> #include<unordered_set> //freopen("in.txt", "r", stdin); using namespace std; typedef double dou; typedef long long ll; typedef pair<ll, ll> pii; #define M 1050 #define inf 0x3f3f3f3f #define mod 1000000007 #define W(a) while(a) #define lowbit(a) a&(-a) #define left k<<1 #define right k<<1|1 #define ms(a,b) memset(a,b,sizeof(a)) #define debug(a) cout<<#a<<" == "<<a<<endl #define false_stdio ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) ll exgcd(ll a, ll b, ll &x, ll &y) { if (!b) { x = 1, y = 0; return a; } ll ans = exgcd(b, a%b, y, x); y -= a / b * x; return ans; } ll solve(ll a, ll b, ll c) { ll x, y, z; z = exgcd(a, b, x, y); if (c%z)return -1;//不成立 //return x; //不需要最小正整数的话直接返回x x *= c / z; b = abs(b / z); return (x%b + b) % b; } int main() { false_stdio; ll a, b, c; cin >> a >> b >> c; ll x = solve(a, b, c); ll y = (c - x * a) / b; if(x>=0)//看x大小要求而定 cout << x << ' ' << y << endl; return 0; }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】