BSGS
全称
Baby Step Gaint Step(大步小步法)
内容
求解 Ax≡B(mod C)(0≤x<C) A x ≡ B ( m o d C ) ( 0 ≤ x < C ) 一类的方程( C C 为素数)。
的证明:
当
C
C
为素数时,根据欧拉定理得
又
A0≡1(mod C)
A
0
≡
1
(
m
o
d
C
)
∴0
∴
0
到
φ(C)
φ
(
C
)
是一个循环节。
∴
∴
如果
x
x
在上无解,那么此方程也无解。
过程
以下默认 gcd(A,C)=1 g c d ( A , C ) = 1 。因为如果 gcd(A,C)≠1 g c d ( A , C ) ≠ 1 ,由于 C C 是素数,就是 C C 的倍数了,这种情况直接特判就好了。
令,那么原式转化为
Ai⋅m+j=B(mod C)
A
i
⋅
m
+
j
=
B
(
m
o
d
C
)
。这时我们只需要枚举
i
i
即可。时间复杂度。
对于枚举出来的
i
i
,设原式转化为
D⋅Aj≡B(mod C)
D
⋅
A
j
≡
B
(
m
o
d
C
)
,用EXGCD就可以求出
D
D
。
求完,接下来就是求
j
j
。我们可以事先把
Aj
A
j
存到哈希表里,然后
O(1)
O
(
1
)
查询。
EXBSGS
内容
求解 Ax≡B(mod C)(0≤x<C) A x ≡ B ( m o d C ) ( 0 ≤ x < C ) 一类的方程( C C 不一定为素数)。
过程
令
则
(a∗d)x≡b∗d(mod c∗d)
(
a
∗
d
)
x
≡
b
∗
d
(
m
o
d
c
∗
d
)
a∗(a∗d)x−1≡b(mod c)
a
∗
(
a
∗
d
)
x
−
1
≡
b
(
m
o
d
c
)
然后我们把多出来的那个
a
a
乘到里面(就是上面的那个
D
D
),就又循环了一遍。
最后原式就变成,令
x=i∗m+j+cnt
x
=
i
∗
m
+
j
+
c
n
t
,然后和BSGS一样做就好了。
但是因为
i≥0,j≥0
i
≥
0
,
j
≥
0
,所以还要枚举
0
0
到这一段。