-
Notifications
You must be signed in to change notification settings - Fork 8
/
Copy pathbaby_step.cpp
65 lines (64 loc) · 1.81 KB
/
baby_step.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <map>
#include <cstring>
const int MOD = 100000007;
int k, ret;
int pow_mod(int a, int b)
{
long long ret = 1;
while(b) {
if(b & 1) {
ret = ret * a % MOD;
}
b >>= 1; a = 1LL * a * a % MOD;
}
return (int)ret;
}
int exgcd(int a, int b, int &x, int &y)
{
int gcd = a;
if(b == 0) {
x = 1;
y = 0;
} else {
gcd = exgcd(b, a % b, x, y);
x -= (a / b) * y;
std::swap(x, y);
}
return gcd;
}
int main()
{
int T, ca = 1;
scanf("%d", &T);
while(T--) {
scanf("%d%d", &k, &ret);
int m = (int)sqrt(1.0 * MOD) + 10;
std::map<int, int> mp;
for(int i = 0; i < m; i++) {
int tmp = pow_mod(k, i);
if(mp.find(tmp) == mp.end()) {
mp[tmp] = i;
}
}
int ans = MOD;
for(int i = 0; i < m; i++) {
int tmp = pow_mod(pow_mod(k, i), m);
int x, y;
exgcd(tmp, MOD, x, y);
while(x < 0) x += MOD;
x = 1LL * x * ret % MOD;
y = 1LL * y * ret % MOD;
if(mp.find(x) != mp.end()) {
tmp = i * m + mp[x];
if(tmp < ans) {
ans = tmp;
}
}
}
printf("Case %d: %d\n", ca++, ans);
}
return 0;
}