关于Miller-Rabbin的一点想法
2017-05-19 12:10
232 查看
在好久之后终于搞完了miller-rabbin素性测试,谈谈自己的理解
要判断的数设为 a,
主要思想就是运用费马小定理来搞,随机几个数x(x<=a-1),判断x^(a-1)=1(mod a)是否成立,如果有不成立,a肯定不是素数
这是有一定错误几率的,随机n个数的错误几率为4^(-n)
这么看来,肯定是多来几组随机数比较保险,10比较稳
期间加入了二次探测定理,以提高miller-rabbin的效率
二次探测定理:若p是奇素数 x^2=1 (mod p) x的解一定为 1或p-1
如果不满足此定理,一样是合数
code
#include<cstdio> #include<algorithm> #include<cstring> #include<queue> #include<cmath> #include<vector> #include<cstdlib> #include<iostream> #include<ctime> #define ll long long #define inf 2147483647 #define N 10 using namespace std; ll quick_mul(ll a, ll b, ll n) { ll res = 0; while(b) { if(b&1) res = (res + a) % n; a = (a + a) % n; b >>= 1; } return res; } ll quick_pow(ll a, ll b, ll n) { ll res = 1; while(b) { if(b&1) res = quick_mul(res, a, n); a = quick_mul(a, a, n); b >>= 1; } return res; } bool miller_rabin(ll x){ if(x==2||x==3||x==5||x==7||x==11)return 1; if(x==1||!(x%2)||!(x%3)||!(x%5)||!(x%7)||!(x%11))return 0; ll n=x-1;int k=0; while(!(n&1)){n>>=1;k++;}//这么做是为了顺便加上二次探测定理 srand((ll)time(0)); for(int i=1;i<=N;i++){ ll t=rand()%(x-1)+1,pre; if(!t)continue; t=quick_pow(t,n,x); pre=t; for(int i=1;i<=k;i++){ t=quick_mul(t,t,x); if(t==1&&pre!=1&&pre!=x-1)return 0; pre=t; } if(t!=1)return 0; } return 1; } int main(){ //freopen(".in","r",stdin); //freopen(".out","w",stdout); int l,r,cnt=0; scanf("%d%d",&l,&r); for(int i=l;i<=r;i++){ if(miller_rabin(i))cnt++; } printf("%d",cnt); return 0; }View Code
相关文章推荐
- 关于用户角色权限的一点想法(1)
- 关于Wiki 的一点想法
- 关于J2SE的一点想法
- 关于下一代IM服务器的一点想法
- 关于通用信息管理类应用软件框架的一点想法(导入不成功,只能考一篇一篇的转咯)
- 关于浮点一点想法和使用
- 关于黄家驹的一点想法
- 关于宋朝及中国历史的一点想法
- 关于网站管理系统的一点想法----关于自定义空件
- (转)关于用户角色权限的一点想法
- 关于LINUX与M$ WINDOWS的一点想法
- 关于.net的一点想法
- 关于用户角色权限的一点想法(2)
- 关于用户角色权限的一点想法(转贴)
- 关于写用.NET Remoting开发分布式应用随笔的一点想法
- 关于SmartClient 与 游戏开发的一点想法
- 关于用户角色权限的一点想法
- 关于用户角色权限的一点想法(1)
- 关于满足顾客需要的一点想法
- 关于SNS规则引擎的一点想法