区间质数转换成区间和数的问题,看到区间只有1e6,所以任务是删去这个区间内所有合数。
每一个合数n最小质因子不会超过。
首先筛出 (1e5)的所有质数,用他们去筛L到R的所有合数即可。
#include <iostream>
#include <iostream>
#include <cstring>
#include <cmath>
#define ms(a,b) memset(a,b,sizeof(a))
#define INF 0x3f3f3f3f
#define LL long long
using namespace std;
const int N=1e6+10;
LL l,r,pri[N],x[N];
bool vis[N];
void prime()
{
ms(vis,0);
pri[0]=0;
for(LL i=2;i<=1e5;i++)
{
if(!vis[i])
pri[++pri[0]]=i;
for(LL j=1;j<=pri[0]&&pri[j]*i<=1e5;j++)
{
vis[pri[j]*i]=1;
if(i%pri[j]==0)
break;
}
}
// for(int i=1;i<=pri[0];i++)
// cout<<pri[i]<<endl;
}
int main()
{
prime();
while(cin>>l>>r)
{
for(LL i=l,p=0;i<=r;i++,p++)
x[p]=0;
for(LL i=1;i<=pri[0]&&pri[i]*pri[i]<=r;i++)
for(LL j=ceil(l/pri[i]);pri[i]*j<=r;j++)
if(j==1) continue;
else x[pri[i]*j-l]=1;
LL maxdis=-1,mindis=INF,pre=-1,maxpos,minpos;
if(l==1)
x[0]=1;
for(LL i=l,p=0;i<=r;i++,p++)
{
if(!x[p])
{
if(pre==-1)
pre=p;
else
{
if(p-pre>maxdis)
{
maxdis=p-pre;
maxpos=pre;
}
if(p-pre<mindis)
{
mindis=p-pre;
minpos=pre;
}
pre=p;
}
}
}
if(maxdis==-1)
cout<<"There are no adjacent primes."<<endl;
else
cout<<minpos+l<<","<<minpos+l+mindis<<" are closest, "<<maxpos+l<<","<<maxpos+l+maxdis<<" are most distant."<<endl;
}
}
int最大是2^31-1
maxn=(1<<31)-1,sqrt(maxn)会报错
运算过程中两个数都是int,相乘溢出后结果不能保证,最好设置成LL