Erathosthenes算法 素数预处理 埃拉托色尼
Erathosthenes算法,它的工作方式如下:输入一个从整数2到N的列表,数字2是第一个质数。所有和2有倍数关系的数字如4,6,8等都不是质数,我们把这些数从列表中排除。接着,2之后的第一个未被删除的数是3,它是第二个质数。所有和3有倍乘关系的数都不是质数,从列表中排除这些数。注意,6已经被排除了,9和12也已经离开了,还有15等。上下的没有被排除的第一个数是接下来的一个质数。算法以这种方式继续运行,直到达到最后一个数N。最后剩下来的数都是质数。
代码:数组实现
#include<iostream> #include<cstdlib> #include<cstring> #include<cstdio> #include<algorithm> using namespace std; typedef long long ll; const ll N=1000000+10; ll prime[N],arr[N],cnt=0; int main() { ll n; //指定范围1~n while(scanf("%I64d",&n)==1) //连续输入 { cnt=0; memset(arr,0,sizeof(arr)); for(ll i=2;i<=n;i++) { if(!arr[i]) prime[cnt++]=i; for(ll j=i*2;j<=n;j+=i) arr[j]=1; } for(ll i=0;i<cnt;i++) cout<<prime[i]<<" "; //输出1~n范围内的所有质数 cout<<endl; } }
vector实现:
#include<iostream> #include<cstdlib> #include<cstring> #include<cstdio> #include<algorithm> #include<vector> using namespace std; typedef long long ll; const ll N=1000000+10; ll prime[N],arr[N],cnt=0; int main() { ll n; //指定范围1~n vector<int> container; while(scanf("%I64d",&n)==1) //连续输入 { cnt=0; memset(arr,0,sizeof(arr)); for(ll i=2;i<=n;i++) { if(!arr[i]) container.push_back(i); for(ll j=i*2;j<=n;j+=i) arr[j]=1; } vector<int>::iterator p; for(p=container.begin();p!=container.end();p++) cout<<*p<<" "; //输出1~n范围内的所有质数 cout<<endl; } }
改进:
#include<iostream> #include<cstdlib> #include<cmath> #include<cstring> #include<cstdio> #include<algorithm> #include<vector> using namespace std; typedef long long ll; const ll N=1000000+10; ll prime[N],arr[N],cnt=0,n; bool B(ll n) { for(int i=0;prime[i]*prime[i]<=n;i++) { if(n%prime[i]==0) return false; return true; } } int main() { //指定范围1~n while(scanf("%I64d",&n)==1) //连续输入 { cnt=0; memset(arr,0,sizeof(arr)); ll k=(ll)floor(sqrt(n)+0.5); for(ll i=2;i<=n;i++) { if(!arr[i]) prime[cnt++]=i; for(ll j=0;j<cnt&&prime[j]*i<=n;j++) { arr[prime[j]*i]=1; if(i%prime[j]==0) break; } } for(ll i=0;i<cnt;i++) cout<<prime[i]<<" "; //输出1~n范围内的所有质数 cout<<endl; } }
版权声明:本文为博主原创文章,未经博主允许不得转载。
posted on 2015-05-15 20:49 Tob__yuhong 阅读(184) 评论(0) 编辑 收藏 举报