数论弱渣学习中,勿喷。。。。
百度百科
数论中的逆元
在模运算中,
加法单位元是0,因为(0+a) mod m = a mod m;
乘法单位元是1,因为(1×a) mod m = a mod m
定义 对a∈Zm,存在b∈Zm,使得a+b ≡ 0 (mod m),则b是a的加法逆元,记b= - a。
定义 对a∈Zm,存在b∈Zm,使得a×b ≡1 (mod m),则称b为a的乘法逆元。
逆元在密码学中有广泛应用,AES密码体系的字节替代就是运用了逆元。
具体计算逆元时,计算加法逆元的方法是很显然的。而对于乘法逆元:在mod m的操作下(即Zm中),a存在乘法逆元当且仅当a与m互质。不定方程ab+mx=1的任意一组整数解(b,x),b就是a的乘法逆元。具体计算可以使用扩展欧几里德算法(Extended-GCD)。
数论的题目中用到逆元的话主要就是乘法逆元了
一个小小的例子
在一连串的加减乘除中有 (a/b)%mod 这样的东东,直接除肯定会错,因为a已经是取模后的结果了
做法是这样的:
(a/b)%mod
let a=b*k
a%mod = b*k %mod
a/b%mod = k % mod;
=> k%mod <=> b*inverse(b) * k % mod
b * inverse(b) 与 1 同余
问题转换成a*inverse(b) % mod;
即求b对mod的乘法逆元
转换一下:
b*x%mod = 1;
b*x = y*mod + 1;
b*x - mod*y = 1;
这个式子其实就可以看出b 与 mod 应该互质
exgcd 解方程求最小正整数解即可
int exgcd(int a,int b,int &x,int &y)
{
if(b==0) {x=1;y=0;return a;}
else
{
int d=exgcd(b,a%b,x,y);
int t=x;
x=y;
y=t-a/b*y;
return d;
}
}
int inverse(int num,int mod)
{
int x,y;
exgcd(num,mod,x,y);
while(x<0) x+=mod,y-=num;
return x;
}
ps:下面的还没有详细去证明。。。。
其实如果P是质数的时候可以用费马小定理来做,即a*b^(mod-2)//这个比较常用
p不是质数的时候是
a*b^(phi(mod)-1)