TZOJ4295--Modular Inverse

发布时间 2023-08-12 18:49:46作者: Feintl

题目简述:

给你一个整数a(0<a<=1000)和一个模数m(0<m<=1000),问是否存在一个正整数x使得a*x%m=1,使x尽可能小。

 标准输入

3
3 11
4 12
5 13

标准输出

4
Not Exist
8

思路1:

暴力,观察数据很显然,x的范围是0~(m-1),由于输出要求x为正整数,当x=0时应输出m。枚举1~m即可,能使得a*x%m=1,那么此时x就是答案,否则输出“Not Exist”。

思路2:

通过逆元来求。由于m保证是质数,所以快速幂求逆元不能用,得用扩展欧几里得求逆元。此时式子转变成 ax+my=gcd(a,m),如果gcd(a,m)不等于1,则不存在逆元。若存在,则x变量就是所求逆元。为了保证x是最小正整数,做这最后一步操作即可(x%mod+mod)%mod。

暴力代码就不展示了。

展示扩欧的代码。

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define IOS ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
 4 #define int long long
 5 typedef unsigned long long llu;
 6 const double e=1e-7;
 7 const int N=1e5+7;
 8 const int MOD=1e9+7;
 9 const int LINF=1e18;
10 const int P=131;
11 bool C=1;
12 
13 int exgcd(int a,int b,int &x,int &y){
14     if(b==0){
15         x=1,y=0;return a;
16     }
17     int X1,Y1,d;
18     d=exgcd(b,a%b,X1,Y1);
19     x=Y1,y=X1-a/b*Y1;
20     return d;
21 }
22 void solve(){
23     int n,m;
24     cin>>n>>m;
25     if(__gcd(n,m)!=1){
26         cout<<"Not Exist"<<endl;
27         return;
28     }
29     int x,y;
30     exgcd(n,m,x,y);
31     x=(x%m+m)%m;
32     if(x==0) x=m;
33     cout<<x<<endl;
34 }
35 signed main(){  
36     IOS;
37     int t;
38     if(C) cin>>t; 
39     else t=1;
40     while(t--) solve();
41 }
View Code