for循环找到素数

时间:2012-06-04 11:42:34

标签: java

我正在尝试运行此代码来打印少于200万的所有素数的总和。这个循环永无止境。谁能告诉我代码有什么问题?它似乎适用于较小的数字。

public static void main(String[] args) {

        long result = 1;

        for(int i=0; i<2000000; i++) {
            if(isPrime(i)) {
                result+= i;
            }
        }
        System.out.println(result);

    }
private static boolean isPrime(long n) {
    boolean result = false;

    for(long i=2; i<(long)Math.sqrt(n); i++) {
        if(n%i == 0) {
            result = false;
            break;
        }
        else result = true;
    }
    return result;
}

5 个答案:

答案 0 :(得分:5)

isPrime中,您只是按2进行分区测试:

private static boolean isPrime(long n) {
    boolean result = false;

    for(long i=1; i<n/2; i++) {
        if(n%2 == 0) {
            result = false;
            break;
        }
        else result = true;
    }
    return result;

}

它应该按每i除以从2开始:

for(long i=2; i<n/2; i++) {
    if(n%i == 0) {
      ...

实际上,在您当前的版本中,奇数n将继续除以2到n/2,而不是更快地停止。考虑n = 21.你将2从1除以1,而不是在第3步除以3并退出。

它不仅会提供不正确的结果,而且还需要比达到return声明所需的时间更长的时间。

编辑:为了获得更快的结果,请查看此Erathostenes方法筛:

public static long sumOfPrimes(int n) {

    long sum = 0;

    boolean[] sieve = new boolean[n];
    for(int i = 2; i < Math.sqrt(n); i++) {
        if(!sieve[i]) {
            for(int j = i * i; j < n; j += i) {
                sieve[j] = true;
            }
        }
    }

    for(int i = 2; i < n; i++) {
        if(!sieve[i]) {             
            sum += i;
        }
    }

    return sum;
}

编辑#2 :发现新版本的一些错误。以下是更正后的内容:

private static boolean isPrime(long n) {
    boolean result = false;

    if(n == 2 || n == 3) return true;

    for (long i = 2; i <= (long) Math.sqrt(n); i++) {
        if (n % i == 0) {
            result = false;
            break;
        } else
            result = true;
    }

    System.out.println(n + " " + result);
    return result;
}

答案 1 :(得分:2)

isPrime()

中有个错误

测试应该是:

if(n%i == 0) { ...

并且您需要从2开始计数,而不是1,因为除以1时,每个数字的余数为零!

此外,无需经过Math.sqrt(n)

您应该将其更改为:

private static boolean isPrime(long n) {
    long max = (long)Math.sqrt(n);
    for (long i = 2; i < max; i++) {
        if (n % i == 0) {
            return false;
        }
    }
    return true;
}

仅供参考,通过此更改,我在我的电脑上测试了该程序,并在1秒内完成,结果为143064094810

答案 2 :(得分:0)

天真isPrime函数必须在每次运行时计算最多i(或至少高达sqrt(i))的所有素数。确保你的isPrime函数缓存其结果!

答案 3 :(得分:0)

经过测试和无错误的Prime检查功能

static boolean isPrime(int n) {
    if (n == 1) return false;

    for(int i = 2; i <= n/2; i++)
        if(n % i == 0)
            return false;

    return true;
}

答案 4 :(得分:0)

以下是使用JOptionPane的Prime的完整程序,即Java GUI

import javax.swing.*;

public class ChkPrime {
    public static void main(String[] args) throws NumberFormatException {
        String str = JOptionPane.showInputDialog(null, "Enter any number: ","Input...", 3);

        try {
            int num = Integer.parseInt(str);


            if (num == 1)
                JOptionPane.showMessageDialog(null, "Your inputed no. " + num + " is not prime.","Error!", 0);

            for(int i = 2; i <= Math.sqrt(num); i++) {
                if(num % i == 0) {
                    JOptionPane.showMessageDialog(null, "Your inputed no. " + num + " is not prime.","Error!", 0);
                    System.exit(0);
                }
            }

            JOptionPane.showMessageDialog(null, "Your inputed no. " + num + " is prime.","Yeh! Got it!", 1);
        }

        catch (NumberFormatException e) {
            JOptionPane.showMessageDialog(null, "Please input numbers...","Error!", 0);
            main(null);
        }
    }
}