• hihocoder 数论二·Eular质数筛法


    数论二·Eular质数筛法

    时间限制:10000ms
    单点时限:1000ms
    内存限制:256MB

    描述

    小Ho:小Hi,上次我学会了如何检测一个数是否是质数。于是我又有了一个新的问题,我如何去快速得求解[1,N]这个区间内素数的个数呢?

    小Hi:你自己有什么想法么?

    小Ho:有!我一开始的想法是,自然我们已经知道了如何快速判定一个数是否是质数,那么我就直接将[1,N]之间每一个数判定一次,就可以得到结果。但我发现这个方法太笨了。

    小Hi:确实呢,虽然我们已经通过快速素数检测将每一次判定的时间复杂度降低,但是N个数字的话,总的时间复杂度依旧很高。

    小Ho:是的,所以后来我改变了我的算法。我发现如果一个数p是质数的话,那么它的倍数一定都是质数。所以我建立了一个布尔类型的数组isPrime,初始化都为true。我从2开始枚举,当我找到一个isPrime[p]仍然为true时,可以确定p一定是一个质数。接着我再将N以内所有p的倍数全部设定为isPrime[p*i]=false。

    写成伪代码为:

    isPrime[] = true
    primeCount = 0
    For i = 2 .. N
    	If isPrime[i] Then
    		primeCount = primeCount + 1
    		multiple = 2
    		While (i * multiple ≤ N)
    			isPrime[i * multiple] = false
    			multiple = multiple + 1
    		End While 
    	End If
    End For
      

    小Hi:小Ho你用的这个算法叫做Eratosthenes筛法,是一种非常古老的质数筛选算法。其时间复杂度为O(n log log n)。但是这个算法有一个冗余的地方:比如合数10,在枚举2的时候我们判定了一次,在枚举5的时候我们又判定了一次。因此使得其时间复杂度比O(n)要高。

    小Ho:那有没有什么办法可以避免啊?

    小Hi:当然有了,一个改进的方法叫做Eular筛法,其时间复杂度是O(n)的。

    输入

    第1行:1个正整数n,表示数字的个数,2≤n≤1,000,000。

    输出

    第1行:1个整数,表示从1到n中质数的个数

    素数筛模板不解释。

    代码:

    #define ll long long
    #include<algorithm>
    #include<iostream>
    #include<iomanip>
    #include<cstring>
    #include<cstdlib>
    #include<cstdio>
    #include<queue>
    #include<ctime>
    #include<cmath>
    #include<stack>
    #include<map>
    #include<set>
    using namespace std;
    const int MAXN=1000010;
    int su[MAXN];
    bool shi[MAXN];
    
    int shai(int n){
        int p=0;
        memset(shi,1,sizeof(shi));
        shi[0]=shi[1]=0;
        for(int i=2;i<=n;i++){
            if(shi[i]){
                su[++p]=i;
                for(int j=2*i;j<=n;j+=i)
                    shi[j]=0;
            }
        }
        return p;
    }
    
    int main(){
        int n;scanf("%d",&n);
        printf("%d",shai(n));
    }
  • 相关阅读:
    Eclipse正确导入第三方project
    面试的基础_01字符串反向操作
    一个简单的实现了智能虚拟女友—图灵机器人
    Notepad++去除代码行号的几种方法
    fastjson将bean转成字符串时首字母变小写问题
    2015第34周二能收发邮件但不能打开网页解决方法
    2015第34周一
    2015第33周日
    2015第33周六
    构建自己的顾问团
  • 原文地址:https://www.cnblogs.com/renjianshige/p/7340927.html
Copyright © 2020-2023  润新知