BSGS及扩展BSGS

BSGS

作用

大步小步法(Baby-Step-Giant-Step,简称BSGS,至于为什么叫大步小步法,不是很清楚啊QAQ),可以较高效的求解形如 AxB(mod C) (C是素数)的同余方程。

方法

ps:接下来讨论的都是(A,C)=1(由于C是素数,所以等价于A不是C倍数)的情况,如果(A,C)>1(A是C倍数),很容易特判掉。
在说BSGS之前,先来证明一个结论:
如果(A,C)=1,那么对于x∈N,有 Ax mod φ(C)Ax(mod C)
证明:因为(A,C)=1,根据欧拉定理,得 Aφ(C)1(mod C)
设k∈N,根据同幂性,得 Akφ(C)1(mod C)
设a∈N且a<φ(C),所以 Akφ(C)+aAa(mod C)
Ax mod φ(C)Ax(mod C) ,得证。
所以如果0<=x<φ(C)无解,之后肯定也无解(循环了)。不过值得一提的是,φ(C)并不是一定最小正周期,随便造点数据都可以验证。

接下来我们正式开始讲BSGS。这个算法实际上是利用了分块思想来优化暴力枚举,令m= C ,我们假设 x=im+j(0<=i<m0<=j<mi,jN) ,那么也就是说 Ax=AimAj

令D= Aim ,则原方程可转化为 DAjB(mod C) 。用扩展欧几里得就可以求出 Aj 了。然而知道 Aj 好像并没有什么用,因为我们要求的是j。所以这里我们要用到巧妙的预处理(分块+预处理大法好!),就是先把 Aj 全部存进哈希表里(map也可以,就是常数大),然后就可以近似 O(1) 求出j了!

扩展BSGS

作用

BSGS只能处理C是素数的情况,太特殊了,应用范围不大。而扩展BSGS可以解决C不是素数的一般情况。

方法

设d=gcd(A,C),那么A,B,C可以表示为A=a*d,B=b*d(如果B不是d的倍数且B!=1则显然无解),C=c*d。也就是说 (ad)xbd(mod cd)
根据同余性质,这个式子可以同除d,得到 a(ad)x1b(mod c) ,如果我们把D*=a(D就是之前的D= Aim ),那么前面就剩下 (ad)x1 了,不停求d=gcd(A,C),然后将B/=d,C/=d(A不变,因为是 Ax ),D*=A/d,num++,直到d=1为止。

最后方程就变成这种形式了: DAxnumB(mod C) 。令x=i*m+j+num,那么和原先的BSGS一样处理就行了。只不过我们会发现由于 0<=i<m0<=j<m ,所以x将会>=num,这就导致0~num-1枚举不到。所以要在最开始枚举一下0~num-1,这个问题就解决了。

模板题

POJ2417以及POJ3243题解传送门

  • 8
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 9
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 9
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值