洛谷 P1835 素数密度
https://www.luogu.org/problemnew/show/P1835
对于40%,对每个数进行最大$O(\sqrt n)$的判断,因为n比较大所以超时。
想到线性筛,然而我们并不能筛到2e9,时间空间都不允许因为2e9素因子最大也到不了50000,我们预处理出2-50000以内的素数,然后对于每一个数,一个一个的出素因子,进行判断,这里放一下代码。
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include <algorithm> #include <iostream> #include <cstring> #include <cstdio> #include <vector> #include <stack> #include <queue> #include <cmath> #include <map> #define LL long long using namespace std; int l,r,cnt; bool p[50006],vis[50006]; int a[50006],tot; void prepare() { for(int i=2;i<=50000;i++) { if(!p[i])a[++tot]=i; for(int j=1;j<=tot&&i*a[j]<=50000;j++) { p[a[j]*i]=1; if(i%a[j]==0)break; } } } int main() { prepare(); scanf("%d%d",&l,&r); for(int i=l;i<=r;i++) { bool f=0; int k=sqrt(i); for(int j=1;a[j]<=k;j++) { if(i%a[j]==0) { f=1; break; } } if(!f)cnt++; } printf("%d",cnt); }
似乎并不是很理想啊,只有90分,那么,我们利用线性筛的思想(用小的素因子来筛大的)。
我们对于每一个质数,最区间内这个数的倍数打上标记,最后统计个数。
然而,你可能会说数据组开不到那么大。
这里我们数组不用开的太大,假设数组为a,那么将l作为数组的第一个元素,这样的话数组最大1000000.
#include <algorithm> #include <iostream> #include <cstring> #include <cstdio> #include <cmath> #include <map> using namespace std; long long l,r,cnt,ans; bool p[50006]; int a[50006],tot; bool vis[1000006]; void prepare() { for(int i=2;i<=50000;i++) { if(!p[i])a[++tot]=i; for(int j=1;j<=tot&&i*a[j]<=50000;j++) { p[a[j]*i]=1; if(i%a[j]==0)break; } } } int main() { prepare(); scanf("%lld%lld",&l,&r); int c=sqrt(r); for(int i=1;i<=tot&&a[i]<=c;i++) { for(long long j=(l/a[i])*a[i];j<=r;j+=a[i]) { if(j>=l&&j!=a[i])vis[j-l]=1; } } for(int i=0;i<=r-l;i++) if(!vis[i])ans++; printf("%lld",ans); }
除特别注明外,本站所有文章均为Manjusaka丶梦寒原创,转载请注明来自出处