扩展欧几里得,求一组解x,y,使得gcd(a,b) = d = a * x + b * y
void ExGcd(int a,int b,int &d,int &x,int &y) { if(b == 0) { x = 1; y = 0; d = a; } else { ExGcd(b,a%b,d,y,x); y -= x*(a/b); } }
扩展欧几里得,求所有解x,y,使得c = a * x + b * y
bool ModeEqual(int a,int b,int c) //解a*x + b*y = c;a*x ≡ c(mod b) { int x,y,d,x0; ExGcd(a,b,d,x,y); if(c%d) return false; //无解 x0 = x * (c/d) % b; for(int i = 1; i < d; ++i) //输出所有解 printf("%d\n",(x0+i*(b/d))%b); return true; }
扩展欧几里得,求a关于n的逆元a^-1,使得a * a^-1 ≡ 1(mod n)
int ModInverse(int a,int n,int &d,int &x,int &y) { ExGcd(a,n,d,x,y); if(1 % d != 0) return -1; //不存在模逆元 int ans = x/d < 0 ? x/d + n : x/d; return ans; //返回模逆元a^-1 }
扩展欧几里得,求解x,满足同余方程组x ≡ Ri(mod Ai)
int ModEquals(int N) //解方程组x ≡ Ri(mod Ai) { int a,b,d,x,y,c,A1,R1,A2,R2; bool flag = 1; //标记是否有解 scanf("%d%d",&A1,&R1); for(int i = 1; i < N; ++i) { scanf("%d%d",&A2,&R2); a = A1, b = A2, c = R2 - R1; ExGcd(a,b,d,x,y); if(c % d != 0) flag = 0; int t = b/d; x = (x*(c/d)%t + t) % t; R1 = A1 * x + R1; A1 = A1 * (A2 / d); } if( !flag ) R1 = -1; return R1; //求出解,-1表示无解 }
扩展欧几里得,求解x,满足高次同余方程A^x ≡ B(mod C)
#define LL __int64 const int MAXN = 65535; struct HASH { int a; int b; int next; }Hash[MAXN*2]; int flag[MAXN+66]; int top,idx; void ins(int a,int b) { int k = b & MAXN; if(flag[k] != idx) { flag[k] = idx; Hash[k].next = -1; Hash[k].a = a; Hash[k].b = b; return; } while(Hash[k].next != -1) { if(Hash[k].b == b) return; k = Hash[k].next; } Hash[k].next = ++top; Hash[top].next = -1; Hash[top].a = a; Hash[top].b = b; } int Find(int b) { int k = b & MAXN; if(flag[k] != idx) return -1; while(k != -1) { if(Hash[k].b == b) return Hash[k].a; k = Hash[k].next; } return -1; } int GCD(int a,int b) { if(b == 0) return a; return GCD(b,a%b); } void ExGcd(int a,int b,int &d,int &x,int &y) { if(b == 0) { x = 1; y = 0; d = a; } else { ExGcd(b,a%b,d,y,x); y -= x*(a/b); } } int Inval(int a,int b,int n) { int x,y,d,e; ExGcd(a,n,d,x,y); e = (LL)x*b%n; return e < 0 ? e + n : e; } int PowMod(LL a,int b,int c) { LL ret = 1%c; a %= c; while(b) { if(b&1) ret = ret*a%c; a = a*a%c; b >>= 1; } return ret; } int BabyStep(int A,int B,int C) //解A^x ≡ B(mod C) { top = MAXN; ++idx; LL buf = 1%C,D = buf,K; int d = 0,temp,i; for(i = 0; i <= 100; buf = buf*A%C,++i) { if(buf == B) return i; } while((temp = GCD(A,C)) != 1) { if(B % temp) return -1; ++d; C /= temp; B /= temp; D = D*A/temp%C; } int M = (int)ceil(sqrt((double)C)); for(buf = 1%C,i = 0; i <= M; buf = buf*A%C,++i) ins(i,buf); for(i = 0,K = PowMod((LL)A,M,C); i <= M; D = D*K%C,++i) { temp = Inval((int)D,B,C); int w; if(temp >= 0 && (w = Find(temp)) != -1) return i * M + w + d; } return -1; //无解 }
时间: 2024-10-11 11:09:23