费马小定理和逆元

InfinityKI Lv2

费马小定理

为素数,,则

逆元

引入

我们知道,在实数域中,一个数 a 的倒数是 a⁻¹,因为 a * a⁻¹ = 1。除以一个数 b 就等价于乘以 b 的倒数,即 a / b = a * (b⁻¹)

在模运算的世界里,我们想做类似的事情。对于一个整数 a 和一个模数 p,我们想找到一个整数 x,使得 (a * x) % p = 1。如果找到了这样的 x,我们就称 x 是 a 在模 p 意义下的 乘法逆元,记作 a⁻¹

有了逆元,我们就可以在模 p 的意义下做除法了: (a / b) % p 就变成了 (a * b⁻¹) % p

重要前提a 在模 p 意义下存在逆元的充要条件是 a 和 p 互质,即 gcd(a, p) = 1

定义

,则称 的逆元

当且仅当 时,逆元存在。

快速幂法

要求 素数

根据费马小定理,

,即 的逆元

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
ll mod;

ll quick_power(ll a, ll k) {
ll res = 1;
while (k) {
if (k & 1)
res = res * a % mod;
a = a * a % mod;
k >>= 1;
}
return res;
}

inline ll inv(ll x) {
return quick_power(x, mod-2);
}

线性方法

inv[i] 的逆元。

inv[i] = (p - p / i) * inv[p % i] % p

1
2
3
4
5
6
7
8
ll mod;
ll inv[MAXN];

void init(){
inv[1] = 1;
for (int i = 2; i <= mod; ++i)
inv[i] = (mod - mod / i) * inv[mod % i] % p;
}

性质

的逆元,则

卢卡斯定理

要求 素数

对于素数 ,有

1
2
3
4
5
6
7
8
9
ll mod;
ll fact[MAX_MOD]; // 阶乘
ll inv(int x); // 逆元

ll C(ll m, ll n) {
if (m > mod || n > mod)
return C(m / mod, n / mod) * C(m % mod, n % mod) % mod;
return fact[n] * inv(fact[m]) * inv(fact[n - m]) % mod;
}
  • 标题: 费马小定理和逆元
  • 作者: InfinityKI
  • 创建于 : 2025-08-06 14:51:13
  • 更新于 : 2025-08-17 19:26:32
  • 链接: http://infinityki.github.io/2025/08/06/费马小定理和逆元/
  • 版权声明: 本文章采用 CC BY-NC-SA 4.0 进行许可。
评论