Generate primes from 1 to n, crashing for n> 300 million

Any suggestions on how I can get this program to work for n = 1 trillion (in addition to doing updates / buying a new computer)?

The error is this: after assembling the executable program (the command line style output window appears), and then quickly closes, and I get the following error: “ProjectPrimes.exe stops working (Windows is looking for a solution to this problem.” I suspect that this is due to memory problems, since I first encountered it at n = 20 million, but that was before I decided to malloc / free the "sieve" array (that is, my "sieve" array is a large array of sizes nx 1 and each element, consisting of 1 or 0).

The program takes ~ 35 seconds to skip the first 300 million integers (16,252,325 primes), so everything is fine, but nothing impressive. As I mentioned, the goal is to be able to generate primes below 1 trillion, so for a long time ...

If it’s appropriate, here are my hardware specifications (in case the goal on this device is unreasonable): 2.40ghz i5, 4gb RAM, 64-bit Windows 7.

Overview of the methodology for those who are not familiar: we use the Sieve of Sundaram approach. Without going into the proof, we first exclude all odd primes below the integer "n" using the sieve function: [2 * (i + j + 2 * i * j) +1 | i <- [1..n / 2], j <- [i..an optimized upper bound]]. Then we discard even numbers (excluding, of course, two). Which leaves us with the simple.

( , ) n? , , (i) n, (ii) n. n .

"" :

int main() {
    long ceiling = 300*1000*1000;
    long *numPrimes;
    long *primes;

    primes = primesToSS(ceiling+1, numPrimes);
    printf("\n\nThere are %d primes below %d.\n\n",*numPrimes,ceiling);

    free(primes);
    return 0;
}

:

//n represents the ceiling, i.e., the integer below which we will generate primes
//cnt* is a pointer which will point the number of primes below n

long* primesToSS( long n, long* cnt ) {

    //initialize sieve by setting all elements equal to 1 (except for 0 and 1)
    long *sieve = malloc(n*sizeof(long));
    initArray(sieve, n, 1);
    sieve[0] = 0; sieve[1] = 0;

    //eliminate all odd composite numbers
    for (int i = 1; i <= n/2; ++i)
        for (int j = i; j <= (n-2*i)/(2*(2*i+1)); ++j)
            sieve[ 2*(i+j+2*i*j)+1 ] = 0;

    //eliminate all even numbers greater than two 
    //and count total number of primes below n
    long numPrimes = 1;
    for (int i = 3; i < n; ++i) {
        if (i % 2 == 0) sieve[i] = 0;
        numPrimes += sieve[i];
    }
    *cnt = numPrimes;

    //create array of primes
    long *primes = malloc(numPrimes*sizeof(int));
    long counter = 0;
    for (int i = 0; i < n; ++i) {
        if (sieve[i] == 1) {
            primes[counter] = i;
            counter++; } 
    }
    free(sieve);
    return primes;
}

void initArray( int* arr, int len, int n ) {
    for( int i = 0; i < len; ++i) arr[i] = n; }
+4
3

:

  • , 1 , , . 8 1 . , .
  • , , , 2, , . 16 1 .
  • , 24 1 , , 1 5 6. modulo ( ), .
  • 1 (10 12) , , 1 (10 6). , 1 .
  • 16 / ( , ), ~ 58 . . ( ), MiB, 1 .

    - 1 .

    , .

+5
long *numPrimes;
...
primes = primesToSS(ceiling+1, numPrimes);
printf("\n\nThere are %d primes below %d.\n\n",*numPrimes,ceiling);

Blastfurnace, ( ) .

long numPrimes;
...
primes = primesToSS(ceiling+1, &numPrimes);
printf("\n\nThere are %d primes below %d.\n\n", numPrimes, ceiling);

... malloc. , :

long *sieve;
initArray(sieve, n, 1);

...

void initArray( int* arr, int len, int n ) {
    for( int i = 0; i < len; ++i) arr[i] = n; }

int long - . :

long *primes = malloc(numPrimes*sizeof(int));

sizeof , , :

long *primes = malloc(numPrimes * sizeof *primes);

.

: } - , .

+3

: 1 1 /8 , . 125000000000 = 119209 = 116 .

200- SWAP-, , , . , .

, , .

. , - 1, .

+2

All Articles