编程任务编号 L: 素数有多少 提高程序的效率

编程任务编号 L: 素数有多少

任务描述

给定的区间[2,n],求其中有素数的个数。

输入

第一行包含一个整数(1 ≤k≤100000),表示测试用例的个数。输入一个整数n(1<=n<=1,000,000);

输出

每个测试用例输出一行,输出区间[2,n]中素数的个数。

输入举例

3
10
20
30

输出举例

4
8
10

注意事项

提示

因为本问题中提问次数最大为10万次,每次问到的最大范围为[2,1000000]次,因此必须注意提高程序的效率,否则将出现“超过时间限制”的错误。

具体注意事项有:

1、为了减少重复计算,利用先计算表格,然后查表的方式解决。即“一次计算,多次查询”。也就是说,可以通过先生成不超过n的素数个数的表,存放在数组a[ ]中,a[k]的值表示不超过k的素数的个数。遇到提问[2,k],直接根据此表回答结果即可。

2、尽量提高“素性测试”的效率。减少循环次数,或者使用素数筛方法。

3、判断n是否存在因子的循环,如果写成如下形式;

for( i=2;i<sqrt(n); i++)
{
     .................
}

这个循环的效率比较低,因为每循环一次都需要重新计算n的平方根,其实这个计算只需要做一次。因此以上循环可以改成如下形式,提高运行效率。

int gen=sqrt(n);
for( i=2; i<=gen; i++ )
{
    .......................
}

#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdbool.h>
int a[1000000],t;
bool prime(int x){
    int i,n=sqrt(x);
    for(i=2;i<=n;i++)
        if(x%i==0)
            return false;
    return true;
}
void table(){
    int i;
    for(i=2;i<=1000000;i++){
        if(prime(i))   t++;
        a[i]=t;
    }
}
int main(){
    int n,p,i,cnt;
    table();
    scanf("%d",&n);
    while(n--){
        scanf("%d",&p);
       printf("%d\n",a[p]);
    }

}
发布了118 篇原创文章 · 获赞 85 · 访问量 48万+

猜你喜欢

转载自blog.csdn.net/c_lanxiaofang/article/details/103504917