zoukankan      html  css  js  c++  java
  • [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("
    ");
        return 0;
    }

    Time:2017-02-07

  • 相关阅读:
    Linux下shell
    分享微博@功能jquery代码及全面解析
    使用C#处理WebBrowser控件中的跨域问题
    Sqler 工具
    ASP.NET Web API批处理器
    Microsoft Academic Search
    C#中delegate对象Equals方法简析
    写一个编译器
    使用.NET中的Action及Func泛型委托
    电子政务数据库管理系统及应用软件系统安全分享(一)
  • 原文地址:https://www.cnblogs.com/SinGuLaRiTy2001/p/6591414.html
Copyright © 2011-2022 走看看