再帰を使用する数のファクタリゼーション

私は数値の階乗を計算する以下の再帰関数を持っています。プログラムはif条件を削除する以外は正常に動作します。なぜ誰かが説明できますか?

これはうまく動作するコードです -

public static long factUsingRecursion(int number) {
    if (number == 1) {
        return 1;
    } else {
        return number * factUsingRecursion(number - 1);
    }
}

if条件(エラーをスローするコード)がなければ、

public static long factUsingRecursion(int number) {
    return number * factUsingRecursion(number - 1);
}

スタックオーバーフローエラーが発生します。

スレッド「main」の例外 java.lang.StackOverflowError    birst.FactorialUsingRecursion.factUsingRecursion(FactorialUsingRecursion.java:10)で

なぜこれが当てはまるのか、専門家に助言を求めてください。

0
longsは正の数に限定されません。コンピュータはあなたが何をするのかを決めるでしょう。そうすれば、関数は数字が1に等しくなると魔法のように止まるわけではありません。if文がなければ関数の後の関数をスタックに押し込んで、これまで帰還と帰結を終わらせる。スタックのオーバーフローが発生するまで、数値は負の無限大に向かいます
追加された 著者 sunrize920,
ヒント:if - withoutをどうやって止めるのですか?
追加された 著者 cpt. jazz,
質問では1つの「受け入れられた回答」しか選択できません。
追加された 著者 rgettman,
すべての再帰は、再帰を終了するための基本条件を常に持つ必要があります。条件が基本条件のみの場合。それ以外の場合、無限回帰になります。
追加された 著者 Rohit Jain,

7 答え

再帰では、再帰を停止する基本ケースが常に存在する必要があります。 if がなければ、基本ケースはなく、何も停止しません。最終的にスタックにはメソッド呼び出しが多すぎ、 StackOverflowError という結果になります。

7
追加された
なぜこれが下落したのですか?
追加された 著者 Rohit Jain,

この行は number 変数を1つ減らします

return number * factUsingRecursion(number - 1);

1のときを除いて number のすべての値を処理します

このコード行はブレーク条件です

if (number == 1) {
        return 1;

}

あなたがstackoverflow例外を回避するのを防ぎます

2
追加された

電話するとどうなるか想像してみてください。

factUsingRecursion(3);

if:

3*factUsingRecursion(2)
3*2*factUsingRecursion(1)
3*2*1

ifなし:

3*factUsingRecursion(2)
3*2*factUsingRecursion(1)
3*2*1*factUsingRecursion(0)
3*2*1*0*factUsingRecursion(-1)
3*2*1*0*-1*factUsingRecursion(-2)
3*2*1*0*-1*-2*factUsingRecursion(-3)
...
And so on... It will not stop until you encounter the StackOverflow error
2
追加された
@ user2341013ようこそ。 btw、StackOverflowで(緑色のチェックマーク)は1つの答えしか受け入れることができないので、最も役立つものを選んでください。あなたはあなたが好きなだけ多くの答えをupvote(上矢印)することができます。
追加された 著者 Paulpro,
本当にありがとう。その非常に明確な今。あなたの迅速な応答を感謝します!
追加された 著者 user2341013,
確かに、私はそれを持っています。ありがとうございました。しかしこの場合、すべての答えが私を助けました;)
追加された 著者 user2341013,

再帰にはベースケースが必要です。それがなければ、それは何度も何度も機能を呼び出すことを止めずに止めることはありません。 ifステートメントベースケースであり、再帰を終了します。そのため、それを削除すると、 StackOverflowError が取得されます。

2
追加された
この回答はなぜ控除されたのですか?
追加された 著者 rgettman,

あなたは return number * factUsingRecursion(number-1);factUsingRecursion(number-1)を残すだけなので、if条件を削除するとプログラムは動作しなくなります。 >ここでは、 return number * factUsingRecursion(number - 1); を呼び出す同じ戻り値が返されます。あなたの関数は常に自分自身を呼び出すので、何かに評価することはできません。条件を設定することにより、関数は再帰的チェーンのある時点で確定値に評価することができ、最初の呼び出しを評価することができます。

1
追加された

終了条件がないという点で、再帰関数を再帰的にするものの1つを失います。

すべての再帰的ソリューションは、3つのルールまたはプロパティを満たしている必要があります。 再帰的な解は、基底のケースを含まなければならない。 再帰的な解は、再帰的なケースを含まなければならない。 再帰的な解決策は基本ケースに向かって進まなければならない。

投稿者:Pythonを使ったデータ構造とアルゴリズム

1
追加された

すべての整数iに対して、i -1で関数を呼び出しています。 Integersaは無限ですので、関数の呼び出しを止めることはありません。例:-1000は-1001を呼び出すでしょう。これは、JVMがスタックにいくつかのスペースを持っている限り、これは継続します。

0
追加された