繁体   English   中英

Return语句无法正确终止递归方法

[英]Return statement does not correctly terminate a recursive method

我有一个方法getNextPrime(int num) ,该方法应该标识该方法接收到的值之后最接近的素数。

如果num是偶数,它将增加它并再次调用自身。 如果它是奇数,它将运行for循环以检查它是否可以被3到num的一半值之间的奇数整除。 如果是,则它将使num增加2,并且该方法将再次调用自身,否则它将返回作为质数的新num值。

问题是,当程序到达return语句时,它将跳至if语句并返回num + 1的原始值。我已经调试了一段时间,但这没有任何意义。 无论我在何处放置return语句,该方法都将跳转到if语句,而不是终止该方法并将值返回到从其调用的位置。

public int getNextPrime(int num){

    if(num % 2 == 0){
        //even numbers are not prime

        getNextPrime(++num);
    }
    else{

        for(int i = 3; i < (num + 1) / 2; i += 2){

            if(num % i == 0) {
                getNextPrime(num += 2); //consider odd numbers only
            }
        }
    }

    return num; //jumps to if and terminates
}

但是,如果我将else语句更改为单独的if语句, 则if(num%2!= 0)起作用。

为什么会这样?

*注意-给该方法的值大于3,则1、2和3是质数这一事实无关紧要。

这里只有一个结构性问题。 到达单个返回不会折叠整个调用堆栈,它只会返回到先前的调用。

您需要保存每次调用getNextPrime()的结果并将其用作返回值,因此实际找到的值将沿着调用链传递回并返回给初始调用者。 照原样,您只返回传入的数字,因为您从未修改过它。

该修复程序是非常简单的修改。 你在哪里

getNextPrime(++num);

... and ...

getNextPrime(num+2);

替换为

return getNextPrime(++num);

... and ...

return getNextPrime(num+2);

您选择的算法的问题在于效率低下。 您只需要使用较小的质数而不是所有奇数,并且仅使用原始数的平方根来测试可除性。

实施是一项练习。

让我们尝试看一下我们使用参数8调用函数时的调用堆栈;

第一个调用是:getNextPrime(8)。 由于数字是偶数,该函数进入if部分,然后使用getNextPrime(9)再次调用自身。 这次,其他部分启动,在for循环中检查可除性,发现9是可整除的,因此调用getNextPrime(11)。 现在,getNextPrime(11)再次进入else和for循环,发现11是质数,并将数字11返回给调用方,但是如果仔细观察,则不会将此值存储在变量中,而num变量存储在getNextPrime调用为9,当getNextPrime(9)返回时,该值返回给getNextPrime(8)。 在getNextPrime(8)中,您也没有真正存储从递归调用堆栈返回的num变量。 您只是返回该函数中定义的num变量,您恰巧在调用getNextPrime(11)之前将其递增,因此该值为9,并返回9。

下面给出了具有相同if else块的更正程序,以供您参考。

public static int genNextPrime(int num) {
    if (num % 2 == 0) {
        num = genNextPrime(++num);
    } else {
        for (int i = 3; i < (num + 1) / 2; i += 2) {
            if (num % i == 0) {
                num += 2;
                num = genNextPrime(num);
            }
        }
    }
    return num;
}

您的return语句工作正常,但是..您将1,2和3遗漏了。 2是偶数质数,而1不是质数。

暂无
暂无

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

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