汇总数字低于200万

时间:2011-02-26 14:35:14

标签: c++ primes

您可能听说过名为Project Euler(projecteuler.net)的网站。我正在解决第一个问题,这些问题非常简单,我正在解决标题中描述的问题。

这不是关于优化或任何事情 - 它需要大约90千分之一秒才能完成。这给了我错误的总数。

有人能帮助我吗?我不知道为什么我得到的答案 - 从数组总数(atotal)和正常加总数(总数) - 是不正确的。他们都显示的答案是947402457,它告诉我的网站是错误的答案。

如果只是措辞,问题就在这里:http://projecteuler.net/index.php?section=problems&id=10

据我所知,当你可以输入你想要查看的素数(从数组中取出)时,最后也很奇怪的是,它给出了正确的答案

#include <cstring>
#include <cstdlib>
#include <iostream>
#include <cmath>
#include <ctime>

typedef unsigned long int bignum;
//there are 666671 primes below two million
int main(){
    using namespace std;
    bignum top = 2000000;
    bignum total = 0;
    bignum atotal = 0;
    //hardcode 2 and 3
    total += 5;
    int inc = 2;
    bignum n = 5;
    double sq = n;
    bignum np = 1;
    bignum *pa = new bignum[top];
    pa[0] = 2;
    pa[1] = 3;
    while (n < top){
        int div = 5;
        int divinc = 2;
        int p = 1;
        //check if number is prime
        //check divisiblity from any possible prime up to the square root of n
        //first hardcode 2 and 3
        if(n%2==0||n%3==0)
            p = 0;
        else{
            while(div<=sqrt(sq)){
                if(n%div==0){
                    p = 0;
                    break;
                }else{
                    div = div + divinc;
                    if(divinc==2) divinc = 4; else divinc = 2;
                }
            }if(p!=0){ //if it's a prime - 0 is not, 1 is prime
                total = total + n;
                np++;
                pa[np] = n;
                //cout << np << " prime number: " << n << endl; //takes too long if it prints everything
            }
        }
        n += inc;
        if(inc==2) inc = 4; else inc = 2;
    }
    for (int c=0;c<=np;c++){
        atotal += pa[c];
    }
    cout << "Total " << top << ": " << total << endl;
    cout << "Array total: " << atotal << endl;
    cout << "Elapsed time: " << clock() << " " << CLOCKS_PER_SEC << "s of a second" << endl << endl;
    while(true){
            int ptoview = 0;
            cout << "Enter the number of the prime you would like to see (you can view every prime number below "<<top<<") ";
            cin >> ptoview;
            if (pa[ptoview-1]){
                if (pa[ptoview-1] < top)
                    cout << ptoview << " prime: " << pa[ptoview-1] << endl;
                else
                    cout << "Too high/low" << endl;
                cout << endl;
            }
        }
    system("PAUSE");
    return 0;
}

2 个答案:

答案 0 :(得分:3)

这是至少一个问题的线索。看看替换时会发生什么:

for (int c=0;c<=np;c++){
    atotal += pa[c];
}

使用:

for (int c=0;c<=np;c++){
    bignum oldatotal = atotal;
    atotal += pa[c];
    if (atotal < oldatotal)
        cout << "Hmmm: " << oldatotal << " " << atotal << endl;
}

我得到类似的东西:

Hmmm: 4294819625 12858
Hmmm: 4294864122 123849
Hmmm: 4294717053 27802
Hmmm: 4294697657 51420
: : :
Hmmm: 4293781002 792849
Hmmm: 4294658253 1676602
Hmmm: 4293686116 710941
Hmmm: 4294706293 1737578
Total 2000000: 947402457
Array total: 947402457

我不会详细介绍,因为这是一个谜题,我假设你想保持它至少有点挑战: - )


是的,你是对的(基于你在下面的评论)所以我会使答案变得不那么钝,所以对其他人来说更有用。

unsigned long类型不足以容纳所有这些素数的总和,因此它就会被包围。

它是否可以保留实际的素数我自己没有检查过,但下一段中的答案也将解决这个问题。

您可能希望尝试将bignum重新定义为“更大”类型,如unsigned long long(如果有)。

答案 1 :(得分:2)

未查看所有内容,但主{while 1循环中未修改sq。这似乎不对。 (顺便说一下,我已经用筛子过滤器去了素数)。