Euler#3项目在Java中花费了很长时间
Euler项目的问题3是: 13195的主要因子为5、7、13和29 数字600851475143中最大的素因子是什么 我的解决方案需要很长时间。我认为我得到了正确的实施;然而,当用大数字进行测试时,我无法看到结果。它永远运行。我想知道我的算法是否有问题:Euler#3项目在Java中花费了很长时间,java,primes,prime-factoring,Java,Primes,Prime Factoring,Euler项目的问题3是: 13195的主要因子为5、7、13和29 数字600851475143中最大的素因子是什么 我的解决方案需要很长时间。我认为我得到了正确的实施;然而,当用大数字进行测试时,我无法看到结果。它永远运行。我想知道我的算法是否有问题: public class LargestPrimeFactor3 { public static void main(String[] args) { long start, end, totalTime;
public class LargestPrimeFactor3 {
public static void main(String[] args) {
long start, end, totalTime;
long num = 600851475143L;
long pFactor = 0;
start = System.currentTimeMillis();
for(int i = 2; i < num; i++) {
if(isPrime(i)) {
if(num % i == 0) {
pFactor = i;
}
}
}
end = System.currentTimeMillis();
totalTime = end - start;
System.out.println(pFactor + " Time: "+totalTime);
}
static boolean isPrime(long n) {
for(int i = 2; i < n; i++) {
if(n % i == 0) {
return false;
}
}
return true;
}
}
public类最大的primefactor3{
公共静态void main(字符串[]args){
长起点、终点、总时间;
长数=600851475143L;
长pFactor=0;
start=System.currentTimeMillis();
for(int i=2;i
有两件事可以提高性能:
static boolean isPrime(long n)
{
for(int i = 2; i <= sqrt(n); i++) // if n = a * b, then either a or b must be <= sqrt(n).
{
if(n % i == 0)
{
return false;
}
}
return true;
}
这里仍然有可以改进的地方,但这需要你去发现。考虑修改num
。享受Euler项目的乐趣:)公共哈希集distinctPrimeFactors(int n)//疯狂快速素因子生成器
{
HashSet factors=新的HashSet();
int lastres=n;
如果(n==1)
{
增加(1);
回报因素;
}
while(true)
{
如果(lastres==1)
打破
int c=2;
while(true)
{
如果(lastres%c==0)
打破
C++;
}
增加(c);
lastres/=c;
}
回报因素;
}
如果您想为一个数字快速生成不同的素数因子,请使用此方法,该方法可使该数字在每次迭代中变小。您可以将int改为long,它应该适合您。虽然不是用Java编写的,但我认为您可能可以理解以下内容。基本上,只需测试奇数因子和一个数的平方根就可以减少迭代次数。下面是一个蛮力方法,它在C#中给出了一个即时结果
static bool OddIsPrime(long oddvalue)//测试一个奇数>=3
{
//只测试奇数除数。
对于(长i=3;i,这里是通过尝试除法进行整数因子分解的伪代码:
define factors(n)
z = 2
while (z * z <= n)
if (n % z == 0)
output z
n /= z
else
z++
output n
定义因子(n)
z=2
而(z*z您应该按找到的每个因子进行除法。然后,当我们按升序枚举可能的因子时,无需测试它们的素性(因此找到的因子不能是复合的,它的因子将被除法)。您的代码将变成:
class LargestPrimeFactor4 {
public static void main(String[] args) {
long start, end, totalTime;
long num = 600851475143L; // odd value is not divided by any even
long pFactor = 1L;
start = System.currentTimeMillis();
for(long i = 3L; i <= num / i; )
{
if( num % i == 0 ) {
pFactor = i;
num = num / i;
}
else {
i += 2;
}
}
if( pFactor < num ) { pFactor = num; }
end = System.currentTimeMillis();
totalTime = end - start;
System.out.println( pFactor + " Time: " + totalTime);
}
}
class LargestPrimeFactor4{
公共静态void main(字符串[]args){
长起点、终点、总时间;
long num=600851475143L;//奇数不除以任何偶数
长pFactor=1L;
start=System.currentTimeMillis();
对于(长i=3L;ipublic class LargestPrimeFactor){
静态布尔isPrime(长n){
对于(长i=2;i您可以对数字进行素因子分解,然后最大的素因子就是答案:
import java.util.ArrayList;
import java.util.Collections;
public class PrimeFactorization {
/* returns true if parameter n is a prime number,
false if composite or neither */
public static boolean isPrime(long n) {
if (n < 2) return false;
else if (n == 2) return true;
for (int i = 2; i < Math.pow(n, 0.5) + 1; i++)
if (n % i == 0)
return false;
return true;
}
/* returns smallest factor of parameter n */
public static long findSmallestFactor(long n) {
int factor = 2; // start at lowest possible factor
while (n % factor != 0) { // go until factor is a factor
factor++; // test the next factor
}
return factor;
}
/* reduces the parameter n into a product of only prime numbers
and returns a list of those prime number factors */
public static ArrayList<Long> primeFactorization(long n) {
ArrayList<Long> primes = new ArrayList<Long>();
// list of prime factors in the prime factorization
long largestFactor = n / findSmallestFactor(n);
long i = 2;
while (i <= largestFactor) {
// for all possible prime factors
// (2 - largest factor of the number being reduced)
if (isPrime(i) && n % i == 0) {
// if this value is prime and the number is divisible by it
primes.add(i); // add that prime factor to the list
n /= i; // divide out that prime factor from the number
// to start reducing the new number
largestFactor /= i; // divide out that prime factor
// from the largest factor to get the largest
// factor of the new number
i = 2; // reset the prime factor test
} else {
i++; // increment the factor test
}
}
primes.add(n); // add the last prime number that could not be factored
Collections.sort(primes);
return primes;
}
}
import java.util.ArrayList;
导入java.util.Collections;
公共类素因子分解{
/*如果参数n是质数,则返回true,
如果为复合或两者都不是,则为false*/
公共静态布尔iPrime(长n){
如果(n<2)返回false;
如果(n==2),则返回true;
对于(inti=2;i 而(i这一款非常好用!!
public class Puzzle3 {
public static void main(String ar[])
{
Long i=new Long("1");
Long p=new Long("600851475143");
Long f=new Long("1");
while(p>=i)
{
if(p%i==0)
{
f=i;
p=p/i;
int x=1;
i=(long)x;
}
i=i+2;
}
System.out.println(f);
}
}这不是完美的解决方案,但它适用于600851475143
public static void main(String[] args) {
long number= 600851475143L;
int rootOfNumber = (int)Math.sqrt(number)+10;
for(int i = rootOfNumber; i > 2; i--) {
if(number % i == 0) {
if(psudoprime(i)) {
System.out.println(i);
break;
}
}
}
}
public static boolean psudoprime(int num) {
for(int i = 2; i < 100; i++) {
if(num % i == 0) {
return false;
}
}
return true;
}
publicstaticvoidmain(字符串[]args){
长编号=600851475143L;
int rootOfNumber=(int)Math.sqrt(number)+10;
对于(int i=根数;i>2;i--){
如果(编号%i==0){
if(伪主(i)){
系统输出打印LN(i);
打破
}
}
}
}
公共静态布尔值psudoprime(int num){
对于(int i=2;i<100;i++){
如果(num%i==0){
返回false;
}
}
返回true;
}
我将从优化您的isPrime
循环开始。只需迭代到I>sqrt(n)
。要添加到Blender,您还可以在for循环之前检查n%2==true..并以I=3开始for循环,然后迭代2(I+=2).A sieve会更快。如果您使用Java,还可以使用frombiginger
类而不是for(int i=2;i
在您的main
方法中。如果您真的想让它运行得更快,请尝试C/C++。它在不到一秒钟的时间内为我运行,并且没有下面建议的优化。作为旁注,project euler是关于优化的,而不仅仅是蛮力。有许多问题在任何时间内都无法使用“简单”解决方案解决(在任何语言中)。你需要弄清楚逻辑上的“捷径”是什么
public class LargestPrimeFactor {
static boolean isPrime(long n){
for(long i=2;i<=n/2;i++){
if(n%i==0){
return false;
}
}
return true;
}
static long LargestPrimeFact(long n){
long largestPrime=0;
for(long i=2;i<Math.sqrt(n)/2;i++){
if(n%i==0){
if(isPrime(i)){
largestPrime=i;
}
}
}
return largestPrime;
}
public static void main(String args[]) {
System.out.println (LargestPrimeFact(600851475143L));
}
}
import java.util.ArrayList;
import java.util.Collections;
public class PrimeFactorization {
/* returns true if parameter n is a prime number,
false if composite or neither */
public static boolean isPrime(long n) {
if (n < 2) return false;
else if (n == 2) return true;
for (int i = 2; i < Math.pow(n, 0.5) + 1; i++)
if (n % i == 0)
return false;
return true;
}
/* returns smallest factor of parameter n */
public static long findSmallestFactor(long n) {
int factor = 2; // start at lowest possible factor
while (n % factor != 0) { // go until factor is a factor
factor++; // test the next factor
}
return factor;
}
/* reduces the parameter n into a product of only prime numbers
and returns a list of those prime number factors */
public static ArrayList<Long> primeFactorization(long n) {
ArrayList<Long> primes = new ArrayList<Long>();
// list of prime factors in the prime factorization
long largestFactor = n / findSmallestFactor(n);
long i = 2;
while (i <= largestFactor) {
// for all possible prime factors
// (2 - largest factor of the number being reduced)
if (isPrime(i) && n % i == 0) {
// if this value is prime and the number is divisible by it
primes.add(i); // add that prime factor to the list
n /= i; // divide out that prime factor from the number
// to start reducing the new number
largestFactor /= i; // divide out that prime factor
// from the largest factor to get the largest
// factor of the new number
i = 2; // reset the prime factor test
} else {
i++; // increment the factor test
}
}
primes.add(n); // add the last prime number that could not be factored
Collections.sort(primes);
return primes;
}
}
ArrayList<Long> primes = PrimeFactorization.primeFactorization(600851475143L);
System.out.println(primes.get(primes.size() - 1));
public class Puzzle3 {
public static void main(String ar[])
{
Long i=new Long("1");
Long p=new Long("600851475143");
Long f=new Long("1");
while(p>=i)
{
if(p%i==0)
{
f=i;
p=p/i;
int x=1;
i=(long)x;
}
i=i+2;
}
System.out.println(f);
}
public static void main(String[] args) {
long number= 600851475143L;
int rootOfNumber = (int)Math.sqrt(number)+10;
for(int i = rootOfNumber; i > 2; i--) {
if(number % i == 0) {
if(psudoprime(i)) {
System.out.println(i);
break;
}
}
}
}
public static boolean psudoprime(int num) {
for(int i = 2; i < 100; i++) {
if(num % i == 0) {
return false;
}
}
return true;
}