逆元
求解一(费马小定理)
是一个质数,并且 ,则有 , ,即可得到逆元。
int quic_pow(int a, int n, int mod) {
int ans = 1;
while(n) {
if(n & 1) ans = (ans * a) % mod;
a = (a * a) % mod;
n >>= 1;
}
return ans;
}
int inv(int a, int p) {
return quick_pow(a, p - 2, p);
}
求解二(拓展欧几里德)
我们知道拓展欧几里德算法可以求解 ,对逆元考虑假设有 那么显然有 ,这不就出来了吗, 就是 模 下的逆元,当然了这里也要有 互质。
int exgcd(int a, int b, int & x, int & y) {
if(!b) {
x = 1, y = 0;
return a;
}
int gcd = exgcd(b, a % b, x, y);
int temp = x;
x = y;
y = temp - a / b * y;
return gcd;
}
int main() {
int a, mod, inv, t;
exgcd(a, mod, inv, t);
return 0;
}
求解三(线性求解逆元)
我们假定有
同时乘以
得
所以我们就推导完了。
int inv[n], mod = 100007, n = mod;
for(int i = 2; i < n; i++) {
inv[2] = ((p - p / i) * inv[p % i]) % mod
}
求解四( 中的逆元求解)
那么我们不难发现
void init() {
fac[0] = 1;
for(int i = 1; i < N; i++)
fac[i] = (fac[i - 1] * i) % mod;
inv[N - 1] = qpow(fac[N - 1], mod - 2);
for(int i = N - 2; i >= 0; i--)
inv[i] = (inv[i + 1] * (i + 1)) % mod;
}