Eratosthenes的筛子和他的素数

时间:2016-11-05 19:57:07

标签: c primes sieve-of-eratosthenes

这是我的代码:

#include <stdio.h>

int main() {
    int number;
    int prime[200000] = { 0 };
    int i = 0;
    int j = 0;
    int number1[200] = { 0 };
    int t = 0;
    int count = 0;
    int newprime2[200][200];
    int counter[200] = { 0 };
    int square;
    int count1;

    while ((scanf("%d", &number) ==  1 ) && (number != 0)) {
        number1[count] = number;
        ++count;
    }
    count1 = count;
    for (count = 0; count < count1; ++count) {
        if (number1[count] < 0) {
            fprintf(stderr, "Error: Invalid input!\n"); 
            return 100;
            break;
        }
        for (i = 0; i < number1[count]; i++) {
            prime[i] = i;
        }
        for (i = 2; (i < (number1[count])); i++) {
            if (prime[i] != 0) {       
                for (j = 2; (j < (number1[count])); j++) {
                    {
                        prime[j*prime[i]] = 0;
                        if (prime[i] * j > (number1[count]))
                            break;
                    }
                }
            }
        }
        t = 0;
        for (i = 2; i < number1[count]; ++i) {
            if ((prime[i] != 0) && (number1[count] % prime[i] == 0)) {
                newprime2[count][t] = prime[i];
                ++t; 
            }
        }
        printf("\n");
        printf("%i is made out of these primes\n", number1[count]);
        counter[count] = 0;
        square = 0;

        for (i = 0; i < t; ++i) {
            while (number1[count] % newprime2[count][i] == 0) {
                number1[count] = number1[count] / newprime2[count][i];
                square++;
            }
            counter[count]++;
            /* if number isn't made out of any of these primes*/
            if (!newprime2[count][i]) {   /*Why is this not working?*/
                printf("%i ", number1[count]);
            }  
            if (counter[count] == 1) {
                printf("%i^%d ", newprime2[count][i], square);
            }  else {
                printf("* %i^%d ", newprime2[count][i], square);
            }
            square = 0;
        }
    }
    printf("\n");

    return 0;
}

例如,我的输入是:1 11 120 8 0

输出如下:

1 is made out of these primes
11 is made out of these primes
120 is made out of these primes
2^3 * 3^1 * 5^1 
8 is made out of these primes
2^3

但输出应如下所示:

1 is made out of these primes
1
11 is made out of these primes
11
...

语句(!newprime2[count][i])表示此数组为空?那为什么它不起作用?为什么我甚至不能使用gcc -pedantic -Wall -Werror -std=c99 -O3?有人能帮助我吗?

3 个答案:

答案 0 :(得分:0)

该行

if (!newprime2[count][i]) 
如果在t==0 - 循环之前for,则未达到

,如果输入为素数或统一,则情况就是如此。只需检查t,如果它为零,则结束。

或者先检查它是否统一或已经在prime

我无法用gcc -pedantic -Wall -Werror -std=c99 -O3重复您的问题。

答案 1 :(得分:0)

查看代码的这一部分:

    t = 0;
    for (i = 2; i < number1[count]; ++i){
        if ((prime[i]!=0) && (number1[count] % prime[i]==0)){
            newprime2[count][t] = prime[i];
            ++t;
        }

如果number1[count]1,那么for循环的正文将无法执行,因此t将保留其值({ {1}})。因此,下一个循环的主体

0

也不会执行。

对于数字 for (i=0; i < t; ++i){ ,此循环的主体执行,但它将执行 nothing ,因为11语句中的条件将< em>总是if 。因此,同样的问题 - false将保持其值t具有相同的结果。

答案 2 :(得分:0)

你的算法既复杂又近似:

  • 您不需要执行筛子来对数字进行分解,您可以只计算除数,复合除数将具有非零余数,因为它们的素因子已经被删除。

  • 筛子不完整:如果200000类型为32位(46341就足够了),那么你会转到int,如果int#include <stdio.h> int main(void) { int number, i, p, n, factors, count; int numbers[200]; for (count = 0; count < 200 && scanf("%d", &number) == 1; count++) { if (number == 0) break; if (number < 0) { fprintf(stderr, "Error: Invalid input!\n"); return 100; } numbers[count] = number; } for (i = 0; i < count; i++) { number = numbers[i]; printf("%d is made out of these primes\n", number); factors = 0; for (p = 2; p * p <= number; p += 1 + (p & 1)) { if (number % p == 0) { n = 0; factors++; do { number /= p; n++; } while (number % p == 0); if (n == 1) printf("%d ", p); else printf("%d^%d ", p, n); } } if (factors == 0 || number != 1) printf("%d", number); printf("\n"); } return 0; } 则会过小64位。

这是一个简化版本:

getchar()