赞
踩
最近新开了一个栏目,打算记一些常见问题的算法,以后说不定有用到可以套用一些。
质数(prime number)又称素数,有无限个。质数定义为在大于1的自然数中,除了1和它本身以外不再有其他因数。
这次我们的例题是:
求n以内的质数。(其中 n是传入的参数)。
这里我们介绍三种常见方法:
1.完全遍历法:
这种算法比较基本,对于每个数n,将n依次从2除到n,然后对余数进行比较,如果余数是0,则除得尽,如果不是0则除不尽,按照质数的定义,只有1和他本身能成为因数也就是除得尽,所以只有除得尽的数不大于两个时,才能是质数。
算法实现:
int n;
int count=0;
cin>>n;
for(int i =2;i<=n;i++){ //i从2开始相应了质数定义中的第一句话。
for(int j = 1;j<=n;j++) //从1开始响应了质数定义中“除了1和其本身外没有其他因数的特点”
if(i&j==0)
count++;
if(count ==2)
cout<<i<<" ";
}
这种算法的好处是符合大多数人的第一反应,和定义契合得比较好,也比较省空间,但问题是假如我这里n输入了1000000+时,这个运算时间是非常长的,其算法复杂度高达1*10^12,小数据可以用遇到大数据就很难实现高效了。
int n;
int count=0;
cin>>n;
for(int i =2;i<=n;i++){ //i从2开始相应了质数定义中的第一句话。
for(int j = 1;j<=sqrt(n);j++) //从1开始
if(i&j==0)
{count++;
if(count==2)
break;
}
if(count ==1)
cout<<i<<" ";
}
#include <vector> using namespace std; vector<int> sieve(int n); //函数声明,求n以内的质数 int main(int argc, char const *argv[]) { int n; cin >> n; vector<int> ans = sieve(n); cout << ans.size() << endl; for (int i = 0; i < ans.size(); i++) { cout << ans[i]; if (i < ans.size() - 1)cout << " "; } cout << endl; return 0; } #include<math.h> vector<int>sieve(int n){ int j; vector<bool> all; vector<int> shuju; for (int k = 0;k<=n;k++) all.push_back(true) ; for(j=2;j<=sqrt(n);j++){ for(int i=2;i*j<=n;i++) all[i*j] = false; } for(int i = 2;i<=n;i++){ if(all[i]) shuju.push_back(i); } return shuju; }
这种方法运算效率非常高,特别是在十万级以上的数中,其牺牲掉的内存不多,但对速度的提升确实是非常显著的。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。