1490.Problem_H
Time Limit: 3000 MS Memory Limit: 32768 KB
Description
Give you a lot of positive integers, just to find out how many prime numbers there are.
There are a lot of cases. In each case, there is an integer N representing the number of integers to find. Each integer won’t exceed 64-bit signed integer, and each of them won’t be less than 2.
For each case, print the number of prime numbers you have found out.
3
2 3 4
Sample Output
2
题意是说给出n个数,问这几个数中有几个素数,然而范围没给说清= =这是选拔赛的一道题,用线性筛选的方法会超时,所以用的队友的板子敲的Miller_Rabin算法,结果一直在RE,到比赛结束也没能找出问题。
现在重新拿出来看,因为之前遇到素数的问题一直都是用线性筛选处理的,所以对这个算法其实我了解的并不多= =这是一种用随机数来进行判断的方法,虽然存在出现错误的可能,但是这个概率非常小,所以可以忽略不计。而在调用这个算法的时候,队友的板子里用到了srand()这个函数,当时选拔赛的环境是G++,而G++中不可以使用这个函数,所以一直在RE,将这句去掉之后就可以A了......好吧,然后再去OJ上交C++的环境就可以过了。代码是敲的队友板子也没什么多说的。
下面AC代码:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<time.h>
using namespace std;
const int S=8;
long long mult_mod(long long a,long long b,long long c)
{
a%=c;
b%=c;
long long ret=0;
long long tmp=a;
while(b)
{
if(b&1)
{
ret+=tmp;
if(ret>c)
ret-=c;
}
tmp<<=1;
if(tmp>c)
tmp-=c;
b>>=1;
}
return ret;
}
long long pow_mod(long long a,long long n,long long mod)
{
long long ret=1;
long long temp=a%mod;
while(n)
{
if(n&1)
ret=mult_mod(ret,temp,mod);
temp=mult_mod(temp,temp,mod);
n>>=1;
}
return ret;
}
bool check(long long a,long long n,long long x,long long t)
{
long long ret=pow_mod(a,x,n);
long long last=ret;
for(int i=1;i<=t;i++)
{
ret=mult_mod(ret,ret,n);
if(ret==1&&last!=1&&last!=n-1)
return true;
last=ret;
}
if(ret!=1)
return true;
else
return false;
}
bool Miller_Rabin(long long n)
{
if(n<2)
return false;
if(n==2)
return true;
if((n&1)==0)
return false;
long long x=n-1;
long long t=0;
while((x&1)==0)
{
x>>=1;
t++;
}
srand(time(NULL));
for(int i=0;i<S;i++)
{
long long a=rand()%(n-1)+1;
if(check(a,n,x,t))
return false;
}
return true;
}
long long factor[100];
int tol;
long long gcd(long long a,long long b)
{
long long t;
while(b)
{
t=a;
a=b;
b=t%b;
}
if(a>=0)
return a;
else
return -a;
}
int main()
{
int T;
long long n,ans;
while(scanf("%d",&T)!=EOF)
{
ans=0;
while(T--)
{
scanf("%I64d",&n);
if(Miller_Rabin(n))
ans++;
}
cout<<ans<<endl;
}
return 0;
}