简体   繁体   English

寻找600851475143中最大的素数?

[英]Finding largest prime number out of 600851475143?

I'm trying to solve problem 3 from http://projecteuler.net . 我正试图从http://projecteuler.net解决问题3。 However, when I run thing program nothing prints out. 但是,当我运行程序时,没有打印出来。 What am I doing wrong? 我究竟做错了什么? Problem: What is the largest prime factor of the number 600851475143 ? 问题:600851475143的最大主要因素是什么?

public class project_3 
{
    public boolean prime(long x)   // if x is prime return true
    {
        boolean bool = false;

        for(long count=1L; count<x; count++)
        {
            if( x%count==0 )
            {
                bool = false;
                break;
            }
            else { bool = true; }
        }
        return bool;
    }

    public static void main(String[] args)
    {
        long ultprime = 0L;  // largest prime value
        project_3 object = new project_3();

        for(long x=1L; x <= 600851475143L; x++)
        {
            if( object.prime(x)==true )
            {
                ultprime = ((x>ultprime) ? x : ultprime);
            }
        }
        System.out.println(ultprime);
    }
}

Not only does your prime checking function always return false ; 您的prime检查功能不仅总是返回false ; even if it were functioning properly, your main loop does not seek the input number's factors at all, but rather just the largest prime smaller or equal to it. 即使它运行正常,你的主循环根本不会寻找输入数字的因子,而只是寻找小于或等于它的最大素数。 In pseudocode, your code is equivalent to: 在伪代码中,您的代码相当于:

foo(n):
    x := 0 ;
    foreach d from 1 to n step 1:
        if is_prime(d):          // always false
            x := d
    return x                     // always 0

is_prime(d):
    not( d % 1 == 0 )            // always false

But you don't need the prime checking function here at all. 但是你根本不需要素数检查功能。 The following finds all factors of a number, by trial division : 以下通过试验部门查找数字的所有因素:

factors(n):
    fs := []
    d  := 2
    while ( d <= n/d ):
        if ( n % d == 0 ): { n := n/d ; fs := append(fs,d) }
        else:              { d := d+1 }
    if ( n > 1 ): { fs := append(fs, n) }
    return fs

The testing for divisibility is done only up to the square root of the number. 可分性测试仅在数字的平方根处进行。 Each factor, as it is found, is divided out of the number being factorized, thus further reducing the run time. 如所发现的,每个因子被分解出被分解的数量,从而进一步减少了运行时间。 Factorization of the number in question runs instantly, taking just 1473 iterations. 所涉及数量的因子分解立即运行,仅需1473次迭代。

By construction all the factors thus found are guaranteed to be prime (that's why no prime checking is needed). 通过构造,所发现的所有因素都保证是素数(这就是为什么不需要进行素数检查的原因)。 It is crucial to enumerate the possible divisors in ascending order for this to happen 1 . 为了实现这一点, 按升序计算可能的除数至关重要1 Ascending order is also the most efficient , because any given number is more likely to have smaller prime factor than larger one. 升序也是最有效的 ,因为任何给定的数字更可能具有比较大的素数小的素因子。 Enumerating the primes instead of odds, though not necessary, will be more efficient if you have an efficient way of getting those primes, to test divide by. 枚举素数代替赔率,虽然没有必要,但如果你有一种有效的方法来获得这些素数,那么它将更有效率。

It is trivial to augment the above to find the largest factor: just implement append as 增加上述内容以找到最大因素是微不足道的:只需实现append

append(fs,d):
    return d

1 because then for any composite divisor d of the original number being factorized, when we'll reach d , we will have already divided its prime factors out of the original number, and so the reduced number will have no common prime factors with it, ie d won't divide the reduced number even though it divides the original. 1 因为那么对于原始数的任何复合除数d被分解,当我们达到d ,我们已经将它的素因子除以原始数,因此减少的数将与它没有共同的素因子,即即使它除以原始数据, d也不会除以减少的数字。

Two things: 两件事情:

1) You are starting count at 1 instead of 2. All integers are divisible by 1. 1)您开始count为1而不是2.所有整数都可以被1整除。

2) You are running an O(n^2) algorithm against a rather large N (or at least you will be once you fix point #1). 2)你正在对一个相当大的N运行一个O(n ^ 2)算法(或者至少你会在你修复点#1时)。 The runtime will be quite long. 运行时间很长。

The whole point of Project Euler is that the most obvious approaches to finding the answer will take so long to compute that they aren't worth running. Project Euler的重点是找到答案最明显的方法需要很长时间来计算它们不值得运行。 That way you learn to look for the less obvious, more efficient approaches. 这样你就可以学会寻找不那么明显,更有效的方法。

Your approach is technically correct in terms of whether or not it is capable of computing the largest prime of some number. 您的方法在技术上是否正确,无论它是否能够计算某个数字的最大素数。 The reason you aren't seeing anything print out is that your algorithm is not capable of solving the problem quickly. 您没有看到任何打印输出的原因是您的算法无法快速解决问题。

The way you've designed this, it'll take somewhere around 4,000,000 years to finish. 你设计这个的方式,需要大约4,000,000年才能完成。

If you replaced the 600851475143 number with say 20 it would be able to finish fairly quickly. 如果用20表示替换600851475143号码,它将能够很快完成。 But you have the 600 billion number, so it's not that simple. 但是你拥有6000亿的数字,所以并非那么简单。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM