数论之高次同余方程(Baby Step Giant Step + 拓展BSGS)
什么叫高次同余方程?说白了就是解决这样一个问题:
A^x=B(mod C),求最小的x值。
baby step giant step算法
题目条件:C是素数(事实上,A与C互质就可以。为什么?在BSGS算法中是要求a^m在%c条件下的逆元的,如果a、c不互质根本就没有逆元。)
如果x有解,那么0<=x<C,为什么?
我们可以回忆一下欧拉定理:
对于c是素数的情况,φ(c)=c-1
那么既然我们知道a^0=1,a^φ(c)=1(在%c的条件下)。那么0~φ(c)必定是一个循环节(不一定是最小的)。既然是%c,那么B一定是0到c-1之间的一个数。最坏的条件下,a的φ(c)以内次方%c的余数各不相同,0<=x<C时一定存在一个x满足条件。根据抽屉原理,如果在大于c的x中出现一个x值满足条件,那在它以前一定有一个更小的x值满足条件。
BSGS的算法是这样的:
首先取m=sqrt(c)向上取整。(为什么取sqrt(c)?我也不是很懂,是为了算法的效率平衡。)
然后先预处理a的0到m次方。
a^x=b ( %c )
设x=i*m+j;
即: i为x/m,j为x%m。
a^(i*m+j)=b;
b * (a^(-m))^i = a^j ( %c )
先枚举j,把右边存起来(Hash 或者 普通数组,下一步用二分查找)
枚举i,如果左边的数值曾经存储过(b * (a^(-m))^i = a^j),则 x=i*m+j。
求a^(-m):(就是a^m的逆元)
有两种方法:
方法一:根据欧拉定理
设A=a^m,那么A^φ(c)==1(%c)
A^(φ(c)-1)*A==1(%c)
到这里已经可以得到A的逆元为A^(φ(c)-1)。
继续推下去,根据c是素数,φ(c)=c-1
那么A的逆元就是A^(c-2)
方法二:相当于解a^m*x-C*y=1,根据拓展欧几里得出x就是逆元。
BSGS主要就是要注意细节,注意要去重(余数相同时只要取较小的一个)。
拓展BSGS
如果a跟c不互质,那该怎么办?
其实只需要加一小段代码就可以。
首先,我们知道:
A%C=B,那么就是A-C*x=B,如果d=gcd(A,C),且B%d==0,那么(A/d)%(C/d)=B/d是成立的。
那么我们就在A与C仍有不为一的公因数的时候,不断地从a^x中拿出一个a与c约分。过程中如果b%d!=0,那么在x>T的时候无解。
LL D=%C; LL g=,d;
while( ( d=gcd(A,C) ) != )
{
if(B%d)return -;
B/=d;C/=d;
g++;D=D*(A/d)%C;
}
最后我们的方程就变为了k*a^(x-g) == b' (%c')
用BSGS解出x后加上g就是答案。
数论之高次同余方程(Baby Step Giant Step + 拓展BSGS)的更多相关文章
- 『高次同余方程 Baby Step Giant Step算法』
高次同余方程 一般来说,高次同余方程分\(a^x \equiv b(mod\ p)\)和\(x^a \equiv b(mod\ p)\)两种,其中后者的难度较大,本片博客仅将介绍第一类方程的解决方法. ...
- POJ 3243 Clever Y (求解高次同余方程A^x=B(mod C) Baby Step Giant Step算法)
不理解Baby Step Giant Step算法,请戳: http://www.cnblogs.com/chenxiwenruo/p/3554885.html #include <iostre ...
- 解高次同余方程 (A^x=B(mod C),0<=x<C)Baby Step Giant Step算法
先给出我所参考的两个链接: http://hi.baidu.com/aekdycoin/item/236937318413c680c2cf29d4 (AC神,数论帝 扩展Baby Step Gian ...
- 【POJ2417】baby step giant step
最近在学习数论,然而发现之前学的baby step giant step又忘了,于是去翻了翻以前的代码,又复习了一下. 觉得总是忘记是因为没有彻底理解啊. 注意baby step giant step ...
- 【学习笔记】Baby Step Giant Step算法及其扩展
1. 引入 Baby Step Giant Step算法(简称BSGS),用于求解形如\(a^x\equiv b\pmod p\)(\(a,b,p\in \mathbb{N}\))的同余方程,即著名的 ...
- [置顶] hdu2815 扩展Baby step,Giant step入门
题意:求满足a^x=b(mod n)的最小的整数x. 分析:很多地方写到n是素数的时候可以用Baby step,Giant step, 其实研究过Baby step,Giant step算法以后,你会 ...
- HDU 2815 Mod Tree 离散对数 扩张Baby Step Giant Step算法
联系:http://acm.hdu.edu.cn/showproblem.php?pid=2815 意甲冠军: watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQ ...
- HDU 2815 扩展baby step giant step 算法
题目大意就是求 a^x = b(mod c) 中的x 用一般的baby step giant step 算法会超时 这里参考的是http://hi.baidu.com/aekdycoin/item/2 ...
- POJ 2417 Discrete Logging ( Baby step giant step )
Discrete Logging Time Limit: 5000MS Memory Limit: 65536K Total Submissions: 3696 Accepted: 1727 ...
随机推荐
- (转)android Fragments详解一:概述
Fragment是activity的界面中的一部分或一种行为.你可以把多个Fragment们组合到一个activity中来创建一个多面界面并且你可以在多个activity中重用一个Fragment.你 ...
- CentOS 6.3 安装以及配置Apache php mysql
准备篇: 1.配置防火墙,开启80端口.3306端口 vi /etc/sysconfig/iptables -A INPUT -m state –state NEW -m tcp -p tcp –dp ...
- 重装win7系统的方法
1.当电脑可以运行的情况下重装系统: 用傻瓜似的重装系统就可以了,这个简单,不在累赘. 2.当电脑打不看的情况下: 2.1 用光盘安装系统,这个有好多教程,不在累赘. 2.2 用U盘安装方法: 2.2 ...
- verilog简易实现CPU的Cache设计
verilog简易实现CPU的Cache设计 该文是基于博主之前一篇博客http://www.cnblogs.com/wsine/p/4661147.html所增加的Cache,相同的内容就不重复写了 ...
- 如何在Quartus II中设置Virtual pin
为了验证FPGA工程中的某个模块的功能和时序的正确性,常常需要对其单独进行验证,但是这些模块通常都与内部的众多信号相连(如系统总线,中断信号线等),往往一个模块的对外接口引脚会多达几百个,对其单独仿真 ...
- Qt窗体关闭时,如何自动销毁窗体类对象
Qt窗体关闭时,如何自动销毁窗体类对象 要对你的窗口设置WA_DeleteOnClose属性,默认的情况下关闭窗口仅仅意味着隐藏它 ImgWindow1->setAttribute(Qt ...
- DSP28335矩阵键盘的检测
#include "DSP2833x_Device.h"#include "DSP2833x_Examples.h"char temp;void gpio_in ...
- 解决ubuntu字体发虚,网页字体发虚
好吧,哥也不知所以然,只是突然间所有东西的字体都发虚了~~后来发现是应该是语言支持搞的鬼,卸载掉下面的东东就没事了 sudo apt-get remove fonts-arphic-ukai ttf- ...
- Js作用域与作用域链详解[转]
一直对Js的作用域有点迷糊,今天偶然读到JavaScript权威指南,立马被吸引住了,写的真不错.我看的是第六版本,相当的厚,大概1000多页,Js博大精深,要熟悉精通需要大毅力大功夫. 一:函数作 ...
- Leetcode-Construct Binary Tree from inorder and preorder travesal
Given preorder and inorder traversal of a tree, construct the binary tree. Note: You may assume that ...