C++第一次作业Problem C: 第几个素数

Problem C: 第几个素数

Time Limit: 2 Sec Memory Limit: 512 MB
Submit: 1166 Solved: 345
Description
已知2是第一个素数,3是第二个、5是第三个……现在编程序求第k个素数是什么?所求素数均小于10000000。

根据素数定理,不超过x的素数的个数近似于x/ln(x),根据标程测得的数据,不超过10000000的素数不到66万5千个。

建议:分配动态内存。

Input
输入多个整数k,至EOF结束。输入不超过50个整数。

本题共5组测试样例,k的范围和个数满足:

第一组:k<=100,不超过10个;

第二组:k<=1000,不超过10个;

第三组:k<=10000,不超过20个;

第四组:k<=100000,不超过30个;

第五组:k<=1000000,不超过50个。

Output
输出第k个素数。

Sample Input
1
2
3
5
10
100
Sample Output
2
3
5
11
29
541
HINT
当你遇到如下编译错误时,可以考虑分配动态内存。
gcc: Internal error: File size limit exceeded (program as) Please submit a full bug report. See <file:///usr/share/doc/gcc-4.4/README.Bugs> for instructions.

做麻了,听完同学讲后又看的网上的代码:

#include <math.h>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
using namespace std;
 
int main() {
    int* ar = (int*)malloc(sizeof(int) * 10000000);
    for(int m = 0; m < 10000000; m++)
        ar[m] = 0;
    int h, i, j, k;
    for (i = 2; i <= sqrt(10000000); i++)
        if (ar[i] == 0)
            for (j = 2 * i; j < 10000000; j += i)
                ar[j] = 1;
    while (scanf("%d", &k) != EOF) {
        h = 0, i = 2;
        while (1) {
            if (ar[i] == 0)
                h++;
            if (h == k) {
                printf("%d\n", i);
                break;
            }
            i++;
        }
    }
}

筛法都带出来了,恶心吐了!

欧拉筛法
*如果i是质数,那么就将它与之前的质数(包括它本身)的乘积筛掉。
*如果i是合数,那么就将它与从2到它最小的质因子之间的质数的乘积分别筛掉。

申:
总之意思就是,我们需要在表里筛除合数,而优化算法的过程就是减少一个数被重复筛的次数: 最简单的是筛掉1+2*n的数,再把剩下的数一个个判定;然后是把所有数字都当作筛子,筛掉他们的倍数;
但事实上,把合数当作筛子时,它的倍数已经被他的质因数晒过了,所以只需要用所有质数当筛子筛一遍;——这就是埃氏筛法;

埃氏筛法仍有不足;比如面对35的时候,它可以被5和7重复筛一次; 所以我们改良一下这个筛的办法,我们从被筛的数出发,所有的数只用它的最小质因数 筛一次,这样就不会有重复被筛的情况。要实现这个效果也就是(上面的欧拉筛法)——这也就是线性筛法,也叫欧拉筛法

今天准备不足紧张的一匹,然后这些算法网上都有讲的比我好的多的,比如https://blog.csdn.net/tktp_ht/article/details/89310614

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值