英语不好还想学编程??逆天之路,不由分说!! 数学太差还想学编程??离经叛道,义无返顾!!
输出1亿内的素数个数只需要5秒左右
事实上i+=2;还是有缺陷的。因为每加几个就会出现其他素数的倍数。可以看一下,密码学相关的AKS算法。
就像产生素数一样,有关文献上有采用随机增量的。
费马小定理结合二次探测的蒙特卡罗概率算法
#include <iostream>
#include <time.h>
#include <assert.h>
const unsigned long MAXSHORT=65536L;
const unsigned long MULTIPLIER=1194211693L;
const unsigned long ADDER=12345L;class RandomNumber{
private:
unsigned long randSeed;
public:
RandomNumber(unsigned long s=0);
unsigned short Random(unsigned long n);
double fRandom();
};//产生随机种子
RandomNumber::RandomNumber(unsigned long s)
{
if(s==0)
randSeed=time(NULL);
else
randSeed=s;
}//产生0:n-1之间的随机整数
unsigned short RandomNumber::Random(unsigned long n)
{
randSeed=MULTIPLIER*randSeed+ADDER;
assert(n!=0);
return (unsigned short)((randSeed >> 16) % n);
}//产生[0,1)之间的随机双精度符点小数
double RandomNumber::fRandom()
{
return Random(MAXSHORT)/double(MAXSHORT);
}
typedef unsigned int uint;void power(uint a,uint p,uint n,uint &result,bool &composite)
{
uint x;
if(p==0)
result=1;
else{
power(a,p/2,n,x,composite);
result=(x*x)%n;
if((result==1)&&(x!=1)&&(x!=n-1))
composite=1;
if(p%2)
result=(result*a)%n;
}
}bool PrimeMC(uint n,uint k=10)
{
RandomNumber rnd;
uint a,result;
bool composite=0;
//对0,1,2,3的特殊处理
if(n==0 || n==1)return 0;
if(n==2 || n==3)return 1;for(int i=1;i<=k;i++){
a=rnd.Random(n-3)+2;
power(a,n-1,n,result,composite);
if(composite||(result!=1))
return 0;
}
return 1;
}
int main()
{
using namespace std;
uint n;
while(cin>>n){
cout<<PrimeMC(n)<<endl;
}
return 0;
}