77924


以下3つのJavaプログラムを実行したとき、想定とは異なる結果になりました。

**想定していた結果:**

[code]

    計算開始
    comb(5, 0)=1
    comb(5, 3)=10
    comb(5, 2)=10
    NegativeNumberException was thrown: -3! can't be calculated.
    BadCombinationException was thrown: 5C6 can't be calculated.
    計算終了
    
[/code]

**実際の実行結果:**

[code]

    :~/java$ java Comb
    計算開始
    comb(5, 0) = 1
    comb(5, 3) = 10
    NegativeNumberException was thrown: -3! can't be calculated.
    
[/code]

### 疑問点

なぜ以下の行がそれぞれ出力されなかったのかを知りたいです。お願いします。

  * `comb(5, 2)=10`
  * `BadCombinationException was thrown: 5C6 can't be calculated.`
  * `計算終了`

* * *

**対象のプログラム:**

[code]

    public class NegativeNumberException extends Exception {
        public NegativeNumberException() {
            super();
        }
    
        public NegativeNumberException(String message) {
            super(message);
        }
    }
    
[/code]

[code]

    public class BadCombinationException extends Exception {
        public BadCombinationException() {
            super();
        }
    
        public BadCombinationException(String message) {
            super(message);
        }
    }
    
[/code]

[code]

    public class Comb {
        public static int fact(int n) throws NegativeNumberException {
            if (n < 0) {  // 負の数の階乗
                // エラーなので、例外を作成して投げる
                throw new NegativeNumberException(n + "! can't be calculated.");
            }
            else if (n == 0) {
                return 1;
            }
            else {
                return n*fact(n-1);
            }
        }
    
        public static int comb(int n, int k)
            throws NegativeNumberException, BadCombinationException {
            if (n < k) {
                throw new BadCombinationException(n + " C " + k 
                                                  + " can't be calculated.");
            }
    
            /* nCk = n!/((n-k)!k!) */
            return fact(n)/(fact(n-k)*fact(k));
        }
    
        /** テスト用mainメソッド */
        public static void main(String args[]) {
            try {
                System.out.println("計算開始");
                        
                int result;
            
                result = Comb.comb(5, 0);
                System.out.println("comb(5, 0) = " + result);
    
                result = Comb.comb(5, 3);
                System.out.println("comb(5, 3) = " + result);
                
                result = Comb.comb(5, -3);
                System.out.println("comb(5, -3) = " + result);
                
                result = Comb.comb(5, 2);
                System.out.println("comb(5, 2) = " + result);
                
                result = Comb.comb(5, 6);
                System.out.println("comb(5, 6) = " + result);
    
                System.out.println("計算終了");
            }
            catch (NegativeNumberException e) {
                System.err.println("NegativeNumberException was thrown: "
                                   +  e.getMessage());
            }
            catch (BadCombinationException e) {
                System.err.println("BadCombinationException was thrown: "
                                   +  e.getMessage());
            }
        }
    }
    
[/code]


CC BY-SA 4.0
2021-07-02T12:33:04.213
77923
2021-07-02T16:37:41.637
2021-07-02T16:37:41.637
3060
46879
question
java
Javaプログラムの出力結果がなぜそうなるのかよくわからない


try-catch節で例外が発生した時点でcatch節に処理が移り、例外発生からcatch節までの正常系の処理は **実行されません。**  
参考: [Javaのtry-catch文を基本から! より良いエラー処理の方法を身に着けよう](https://engineer-club.jp/java-
try-catch#i)

それはtry-catch節の中から呼び出したメソッドでthrowされた例外でも上記の挙動となります。  
デバッガを使ってステップ実行すると分かりやすいですが、今回は`result = Comb.comb(5,
-3);`のコードから呼び出される`fact(-3)`の処理で`NegativeNumberException`例外が発生しています。  
その直後に`catch (NegativeNumberException e)`ブロックに処理が移動するので

> comb(5, 2)=10  
>  と  
>  BadCombinationException was thrown: 5C6 can't be calculated.  
>  と  
>  計算終了

を出力する処理は全てスキップされます。


CC BY-SA 4.0
2021-07-02T12:57:24.927
77924
2021-07-02T12:57:24.927
9820
77923
answer