Miller-Rabin素数判定

用费马小定理进行素数判定

1、利用费马小定理

对于素数 p 和与其互质的 a,存在 a p − 1 ≡ 1   ( m o d    p ) {a}^{p-1}\equiv 1\ (mod\ \ p) ap11 (mod  p)

那么,如果选取 a,小于 p,如果符合上述公式,这个 p 是不是素数?

这个不可以,比如341,这种数被称为费马伪素数。

2、随机选取

如果这个 a 是随机选取,并且选取几个去验证,是否可以?

也是不可以,比如 561,这种数被称为卡迈克尔数,在 [ 2 ,   p − 1 ] [2,\, p-1] [2,p1] 范围内都满足上述公式。

3、总结

存在m,a

m 是奇数

2 < = a < = m − 2 2<=a<=m-2 2<=a<=m2

g c d ( a ,   m )   =   1 gcd(a,\, m)\, =\, 1 gcd(a,m)=1

a m − 1 ≡ 1   ( m o d    m ) {a}^{m-1}\equiv 1\ (mod\ \ m) am11 (mod  m)

那么 m 至少有 1/2 的概率是素数

二次探测定理

1、内容

存在 p,x

p 是素数

x 2 ≡ 1   ( m o d    p ) {x}^{2}\equiv 1\, (mod\, \, p) x21(modp)

x < p

那么

x = 1

x = p - 1

2、证明

x 2 ≡ 1   ( m o d    p ) {x}^{2}\equiv 1\, (mod\, \, p) x21(modp)

x 2 − 1 ≡ 0   ( m o d    p ) {x}^{2}-1\equiv 0\, (mod\, \, p) x210(modp)

( x + 1 ) ( x − 1 ) ≡ 0   ( m o d    p ) (x+1)(x-1)\equiv 0\, (mod\, \, p) (x+1)(x1)0(modp)

p ∣ ( x − 1 ) ( x + 1 ) p|(x-1)(x+1) p(x1)(x+1)

Miller-Rabin素数判定

时间复杂度

按照我后面给的代码,应该是 O ( k ( l o g 2 n + l o g n ) ) O(k({log}^{2}n + {log}n)) O(k(log2n+logn))

k 为选取基数 x 的次数,log 是在底数为 2 的意义上。

2 63 {2}^{63} 263 的数据范围,复杂度降到了 63 2 {63}^{2} 632

备注: 2 63 {2}^{63} 263 已经要开 unsigned long long 了。

思路

Fermat素数判定和二次探测定理的结合。

对于待检验数 p,随意选取基数 x:

x、p 符合费马小定理

对于 x p {x}^{p} xp 的开方,只有两种结果:1 或 p - 1

对于奇素数,对 x p {x}^{p} xp 不断开方,要么一直是 1   ( m o d    p ) 1\, (mod\, \, p) 1(modp),要么出现一个 p - 1 之后都是 1。

(本质而言,p - 1 在模 p 的情况下就是 -1,1 的开方即为 ± 1 \pm 1 ±1

代码

inline ll quick_multi(ull x, ull y, ull p)		// O(1)快速乘
{
    return (x * y - (ull)((lb) x / p * y) * p + p) % p;
}

ll quick_pow(ll x, ll y, ll p)			//O(logn)快速幂
{
    ll sum = 1;
    x%= p;
    while (y)
    {
        if (y & 1) sum = quick_multi(sum, x, p);
        x = quick_multi(x, x, p);
        y>>= 1;
    }
    return sum;
}

inline bool mr(ll x, ll p)  // mille rabin判质数
{              
    if (quick_pow(x, p - 1, p) != 1) return 0;  //费马小定理,快速幂
    ll y = p - 1, z;
    while (!(y & 1))    //二次探测
    {  
        y >>= 1;
        z = quick_pow(x, y, p);
        if (z != 1 && z != p - 1) return 0;
        if (z == p - 1) return 1;
    }
    return 1;
}

inline bool prime(ll x) 
{
    if (x < 2) return 0;  // mille rabin判质数
    if (x == 2 || x == 3 || x == 5 || x == 7 || x == 43) return 1;
    return mr(2, x) && mr(3, x) && mr(5, x) && mr(7, x) && mr(43, x);
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值