题目
让我们定义dn为:dn=pn+1−pn,其中pi是第i个素数。显然有d1=1,且对于n>1有d
n是偶数。“素数对猜想”认为“存在无穷多对相邻且差为2的素数”。
现给定任意正整数N(<10^5),请计算不超过N的满足猜想的素数对的个数。
输入格式:
输入在一行给出正整数N。
输出格式:
在一行中输出不超过N的满足猜想的素数对的个数。
输入样例:
20
输出样例:
4
题解
题目意思大致是找出给定n范围内的相邻素数差为2的对数,自然而然想到埃氏筛法
埃氏筛法
第一步:就是将2到n里面的所有整数写下来,其中最小的数就是2咯。
|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|
第二步:就是将2的倍数都删去,现在最小的就是3咯
|2|3|5|7|9|11|13|15|17|19|
第三步:然后再将3的倍数删掉,最小的就是5
|2|3|5|7|11|13|17|19|
以此类推,当表中最小的数字就是m的时候,m就是素数。然后将m的倍数删去,像这样反复操作,就能依次枚举出n以内的素数。
伪代码如下:
bool is_prime[maxn];
int prime[maxn];
int cnt=0;
for(int i=0;i<maxn;i++)
is_prime[i]=true;
is_prime[0]=false;is_prime[1]=false;//0,1不是素数
for(int i=2;i<maxn;i++){
if(is_prime[i){
prime[cnt++]=i;
for(int j=2*i;j<maxn;j+=i)
is_prime[j]=false;
}
}
这样,素数就都存于一个小于给定范围内的数组里面,只要判断相邻的素数是否相差为2即可
#include <iostream>
using namespace std;
const int maxn=100005;
bool is_prime[maxn];
int prime[maxn];
int cnt=0;
void set_prime(int n){
for(int i=1;i<=n;i++)
is_prime[i]=true;
is_prime[1]=false;
for(int i=1;i<=n;i++){
if(is_prime[i]){
prime[cnt++]=i;
for(int j=i;j<=n;j+=i)
is_prime[j]=false;
}
}
}
int main(){
int n;
cin>>n;
set_prime(n);
int count=0;
for(int i=0;i<cnt;i++){
if(i+1<cnt&&prime[i+1]-prime[i]==2)
count++;
}
cout<<count<<endl;
return 0;
}