[SinGuLaRiTy] 米勒羅賓素數判定法


【SinGuLaRiTy-1003】 Copyright (c) SinGuLaRiTy 2017. All Rights Reserved.

背景

數論學家利用費馬小定理研究出了多種素數測試辦法,Miller-Rabbin 素數測試算法是其中較快的一種。

步驟

(1)計算奇數M,使得N=2^r * M + 1;

(2)選擇隨機數A<N;

(3)對於任意i<r,若A^(2^i*M) mod N = N - 1,則N通過隨機數A的測試;

(4)或者,若A^M mod N = 1,則N通過隨機數A的測試;

(5)讓A取不同的值對N進行行多次測試(一般要求5~10次,有較高要求的話可以進行20~30次),若全部通過則判定N為素數;

概率

若N通過一次測試,則N不是素數的概率為25%;

若N通過 t 次測試,則N不是素數的概率為1/( 4 ^ t );

事實上,當 t = 5 時,N不是素數的概率已為1/128,已經大於99.99%。

在實際運用中,可首先用300~500個小素數對N進行測試,以提高測試通過的概率與算法的速度。在隨機生成的素數中,選取的隨機數最好讓 r = 0,則可以省去步驟(3)的操作,進一步減少判定時間。

代碼

#include<cstdlib>
#include<ctime>
#include<cstdio>
using namespace std;
const int count=10;
int modular_exp(int a,int m,int n)
{
    if(m==0)
        return 1;
    if(m==1)
        return (a%n);
    long long w=modular_exp(a,m/2,n);
    w=w*w%n;
    if(m&1)
        w=w*a%n;
    return w;
} 
bool Miller_Rabin(int n)
{
    if(n==2)
        return true;
    for(int i=0;i<count;i++)
    {
        int a=rand()%(n-2)+2;
        if(modular_exp(a,n,n)!=a)
            return false;
    }
    return true;
}
int main()
{
    srand(time(NULL));
    int n;
    scanf("%d",&n);
    if(Miller_Rabin(n))
        printf("Probably a prime.");
    else
        printf("A composite.");
    printf("\n");
    return 0;
}

 

Time:2017-02-07


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM