筛法

筛法

筛选法又称筛法,具体做法是:先把N个自然数按次序排列起来。1不是质数,也不是合数,要划去。第二个数2是质数留下来,而把2后面所有能被2整除的数都划去。2后面第一个没划去的数是3,把3留下,再把3后面所有能被3整除的数都划去。3后面第一个没划去的数是5,把5留下,再把5后面所有能被5整除的数都划去。这样一直做下去,就会把不超过N的全部合数都筛掉,留下的就是不超过N的全部质数

第一种:Eraosthenes(埃拉托斯尼筛法)埃氏筛法

时间复杂度O(nlogn)

利用当前已经找到的素数,从后面的数中筛去当前素数的倍数

#include<stdio.h>
#include<iostream>
#include<memory.h>
#define MAX 100
using namespace std;
int prime[MAX];
void Eratosthenes(){
  for(int i = 0; i < MAX; ++i)
    prime[i] = 1;
  prime[0] = prime[1] = 0;
  for(int i = 2; i < MAX; ++i){
    if(!prime[i])
      continue;
    for(int j = i * 2; j < MAX;j += i)
      prime[j] = 0;
  }
}
int main(int argc, char const *argv[])
{
  memset(prime, 0, sizeof(prime));
  Eratosthenes();
  for(int i = 1; i <= MAX; ++i){
    if(prime[i] == 1)
      printf("%d\n", i);
  }
  return 0;
}

第二种:欧拉筛法

时间复杂度O(n)

和埃氏筛法的区别是对于每一个要筛除的数,欧拉筛法只筛除一次

#include<stdio.h>
#include<iostream>
#define MAX 100
using namespace std;
int check[MAX];
int prime[MAX];
int tot = 0;
void euler(){
  for(int i = 2; i <= MAX; ++i){
    if(!check[i]){
      prime[++tot] = i;
    }
    for(int j = 1; j <= tot && i * prime[j] <= MAX; ++j){
      check[i * prime[j]] = 1;
      //合数标为1,同时,prime[j]是合数i*prime[j]的最小素因子
      if(i % prime[j] == 0)
        break;
       //即比一个合数大的质数和该合数的乘积可用一个更大的合数和比其小的质数相乘得到
    }
  }
}
int main()
{
  euler();
  for(int i = 1; i <= tot; ++i)
    printf("%d\n", prime[i]);
  return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

窗外藏深海

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值