すのはら荘春原庄的雪

埃氏筛和欧拉筛

Toretto·2022-04-13 18:04·297 次阅读

埃氏筛和欧拉筛

1.埃氏筛

思路:将所求范围内所有的数定义为素数,从最小的真实素数(即2)开始,将其倍数筛选出来定义为非素数,最后剩下的被定义为素数的数便是给定范围内所有的素数。

代码:

复制代码
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 bool prime[1000];
 4 int n;
 5 void getprime()
 6 {
 7     for(int i=2;i<=n;i++)
 8         prime[i]=true;
 9     for(int i=2;i<=sqrt(n);i++)
10     {
11         if(prime[i]){
12             for(int j=i*i;j<=n;j+=i)
13             {
14                 prime[j]=false;
15             }
16         }
17     }
18 }
19 int main()
20 {
21     ios::sync_with_stdio(false);
22     cin.tie(0),cout.tie(0);
23     cin>>n;
24     getprime();
25     for(int i=1;i<=n;i++)
26     {
27         if(prime[i])
28             cout<<i<<' ';
29     }
30     return 0;
31 }
复制代码

 

 

 

2.欧拉筛

当数据过多的时候埃氏筛的弊端便体现了出来,即他会重复标记一个数不是素数的倍数,即当素数是2时18会被标记为不是素数,而当素数为3时18会再次被标记为不是素数,因此会导致数据过大时重复次数过多时间过长的问题。而这时欧拉筛便很好的解决了这一弊端。

思路:其实欧拉筛并没有那么繁琐,大致就是从2开始剔除倍数,但是省略了重复标记的过程,具体看代码。

 

复制代码
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 const int maxn=1e5+1;
 4 typedef long long ll;
 5 ll n,k;
 6 bool a[maxn];//判断是否是素数。
 7 int prime[maxn];//用来存素数。
 8 void getprime()
 9 {
10     a[0]=true,a[1]=true;//1和0不是素数,直接标记即可。
11     for(int i=2;i<=maxn;i++)
12     {
13         if(!a[i])//如果没有被标记为true,就是素数。
14             prime[++k]=i;
15         for(int j=1;j<=k;j++)
16         {
17             if(i*prime[j]>maxn)
18                 break;
19             a[i*prime[j]]=true;//用素数一次乘i,结果标记为true。
20             if(!i%prime[j])//节省时间最关键的一步,即只标记一次。
21                 break;
22         }
23     }
24 }
25 int main()
26 {
27     ios::sync_with_stdio(false);
28     cin.tie(0),cout.tie(0);
29     cin>>n;
30     getprime();
31     for(int i=1;i<=n;i++)
32         cout<<prime[i]<<' ';
33     return 0;
34 }
复制代码

 

posted @   cbmango  阅读(297)  评论(1编辑  收藏  举报
相关博文:
阅读排行:
· 在鹅厂做java开发是什么体验
· 百万级群聊的设计实践
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战
· 永远不要相信用户的输入:从 SQL 注入攻防看输入验证的重要性
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
点击右上角即可分享
微信分享提示