题目描述:
一个区间,[L,U], U-L<1e6. 并且U>L. U和L int范围内.问在L到U内相邻最近的两个相邻质数和相邻最远的两个相邻质数.
题解:
区间长度小于1e6,然后合数一定有小于2^16的质因子. 先搞出来2^16的质因子然后乘筛出合数.
重点:
代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
#include <cmath>
#include <ctype.h>
#include <limits.h>
#include <cstdlib>
#include <algorithm>
#include <vector>
#include <queue>
#include <map>
#include <stack>
#include <set>
#include <bitset>
#define CLR(a) memset(a, 0, sizeof(a))
#define REP(i, a, b) for(ll i = a;i < b;i++)
#define REP_D(i, a, b) for(ll i = a;i <= b;i++)
typedef long long ll;
using namespace std;
const ll maxn = 1e6+100;
const ll INF = 1e9;
ll vis[maxn];
ll l, r;
ll pos;
ll pn, p[maxn];
void getP()
{
pn=0;
CLR(vis);
ll key = 1e5;
REP_D(i, 2, key)
{
if(vis[i]==0)
{
p[pn++]=i;
}
for(ll j=0;j<pn&&p[j]*i<=key;j++)
{
ll tmp = i*p[j];
vis[tmp] = 1;
if(i%p[j]==0)
{
break;
}
}
}
}
void solve()
{
pos = l;
CLR(vis);
REP(i, 0, pn)
{
ll t = p[i];
ll a = (l+t-1)/t;
a = max(2LL, a);
ll b = (r)/t;
for(ll j=a;j<=b;j++)
{
ll m = j*t - pos;
vis[m]=1;
}
}
ll last=0, ans_i=0, ans_j=0, ans_l=INF;
for(ll i=l-pos;i<=r-pos;i++)
{
if(vis[i]==0)
{
if(last!=0)
{
if(i+pos-last < ans_l)
{
ans_i = last;
ans_j = i+pos;
ans_l = ans_j -ans_i;
}
}
last = i+pos;
}
}
if(ans_l==INF)
{
printf("There are no adjacent primes.\n");
return;
}
else
{
printf("%I64d,%I64d are closest, ", ans_i, ans_j);
}
last=0, ans_i=0, ans_j=0, ans_l=0;
for(ll i=l-pos;i<=r-pos;i++)
{
if(vis[i]==0)
{
if(last!=0)
{
if(i+pos-last > ans_l)
{
ans_i = last;
ans_j = i+pos;
ans_l = ans_j -ans_i;
}
}
last = i+pos;
}
}
printf("%I64d,%I64d are most distant.\n", ans_i, ans_j);
}
int main()
{
// freopen("1Ain.txt", "r", stdin);
//freopen("1Aout.txt", "w", stdout);
getP();
while(scanf("%I64d%I64d", &l, &r) != EOF)
{
if(l==1)
{
l = 2;
}
solve();
}
return 0;
}