我正在制作一个素数查找器,它会找到用户输入的给定数字的素数。我现在似乎要么错过素数,要么将非素数添加到ArrayList。我的代码对我来说似乎合乎逻辑,而且我很困惑为什么会发生这种情况。谁能告诉我我做错了什么?或者可能是一种更简单的方法(我觉得我过于复杂)?一些错误的例子是:输入21,只有3个显示为素数。输入11000,25和55显示(显然不是素数)。提前谢谢!
import java.util.*;
public class PrimeFactors {
public static void main(String args[]) {
long num;
Scanner in = new Scanner(System.in);
System.out.println("\n\n\nThis program finds the prime factors of a given number.\n");
System.out.print("Please enter the number: ");
num = in.nextLong();
System.out.println("\nThe prime factors are: " + primeFactor(num) + "\n");
}
public static ArrayList<Long> primeFactor(long n) {
long output = 0;
long guess = 2;
ArrayList<Long> primeFactors = new ArrayList<Long>();
while (guess <= n) {
long primes = 0;
long i = 2;
long x = 0;
long rt = 1;
long duplicate = 0;
output = n % guess;
// Finds the sqrt.
while (x <= n) {
x = rt * rt;
rt++;
}
// Finds odd factors.
if ((output == 0) && (guess % 2 != 0)) {
// This divides the odd factor by an incrementing number that is not 1 or the number itself.
while (i < rt) {
primes = primes + (guess % i);
// If the sum of the remainders to the division is not 0, then the number is prime.
// I used duplicate to make sure it didn't just go through once and count as prime.
if (primes != 0){
// There were duplicates, so I added them for the division later.
duplicate = duplicate + guess;
// This was used to wait for the while loop to finish, then find if the amount of times the guess went through was equal to its value - 1 and another 1 for the final number (primes are only divisible by one and itself).
if (i == (factors - 1)) {
if ((duplicate / guess) == (guess- 2)) {
primeFactors.add(guess);
}
}
}
i++;
}
}
guess++;
}
return primeFactors;
}
}
答案 0 :(得分:0)
首先,而不是
long x = 0;
long z = 1;
while (x <= n) {
x = z * z;
z++;
}
while (j < z) {
你可以这样做
z = (int) Math.Sqrt(n)
while (j <= z) {
然后对于每个j,我会检查它是否除以n而没有余数。
如果它将n除以n而没有余数,则将n除以j并将j加到素因子上。然后,不是递增j,而是再次尝试相同的j,例如9,你为它的因子做3次。
任何比这更复杂的东西都是不必要的 - 你会尝试每个j,直到它不再分成n,并且你总是会在由这些素数组成的复合材料之前尝试素数,所以你知道了你最终会得到的结果只有素数因素。
答案 1 :(得分:0)
好的,您的代码存在一些问题:
System.out.println()
来电在哪里,以便您可以看到代码中发生了什么?我可以建议你看看这个:http://en.wikipedia.org/wiki/Sieve_of_Eratosthenes以便快速找到素数。
答案 2 :(得分:0)
使代码更简单的一个建议。在你的primeFactors方法中,首先找出它是一个因素,我相信你已经在做了,然后调用另一个方法来确定这是否是一个素数。如果这是素数加入列表。
答案 3 :(得分:0)
我会给你一些伪代码,用于简单实现(非效率)算法:
the value to factorize is N
keep going until N is equal to one
start at 2 and find lowest number X that divides N evenly
X is one factor
N/X is your new N to factor
答案 4 :(得分:0)
factors
特别糟糕,因为它只是对单一因素的猜测。改为称呼guess
。factors
,primes
和dup
执行的算法也很奇怪。为什么要添加到dup
或primes
?尝试成为自己的计算机,并执行12号算法;你会发现你根本就没有正确的算法。factors
来阻止重复因素的可能性。答案 5 :(得分:0)
你在这里做的数学和逻辑很奇怪,我不太关注正在发生的事情。
为此,我会投票+1以使代码更简单。这可以通过两种简单的方法完成。第一种方法将找到数字的因子并通过质数检查器运行它们。如果它们是一个因素并通过了主要检查,它们就会被添加到数组中。
奖励积分:仅通过搜索每个因子检查器和质量检查器的下半部分来提高算法的速度。逻辑是超过一半数字的任何值都不能成为该数字的一个因素。
更多的速度奖励积分,2跳过所有2的倍数,因为它们自动不是素数。祝你好运!
import java.util.ArrayList;
import java.util.Scanner;
/***************************************************
*
* @file: PrimeFactors.java
* @date: Mar 17, 2013
* @author: AaronW
*/
/**
*
* @author AaronW
*/
public class PrimeFactors {
public PrimeFactors() {
}
/**
*
* @param args
*/
public static void main(String[] args) {
long num;
Scanner in = new Scanner(System.in);
System.out.println("\n\n\nThis program finds the prime factors of a given number.\n");
System.out.print("Please enter the number: ");
num = in.nextInt();
System.out.println("\nThe factors are: " + findFactors((double)num) + "\n");
}
public static ArrayList<Integer> findFactors(Double num) {
ArrayList<Integer> factors = new ArrayList<Integer>();
for (int x = 1; x <= num; x++) {
System.out.println("Testing " + num + " % " + x + " = " + num % x);
// First, let's see if a number is factor of your target number
if (num % x == 0) {
System.out.println(x + " is a factor");
// Now that we know it's a factor, let's test to see if it's prime
if (isPrime(x)) {
// If it's prime, add it to the ArrayList
System.out.println("And " + x + " is prime.");
factors.add(x);
} else {
System.out.println("But " + x + " is not prime.");
}
} else {
System.out.println(x + " is not a factor");
}
}
return factors;
}
public static boolean isPrime(double num) {
// Let's start by assuming everything is prime and try to prove that false
// If we fall through the loop without proving it false, we have a prime
boolean prime = true;
for (int x = 2; x < num; x++) {
// if our target number can be divided by any number between 1 and itself, it is not prime
if (num % x == 0) {
prime = false;
}
}
return prime;
}
}