【解決方法】配列バインドされた実行を見つけました


import java.util.*;
import java.lang.*;
import java.io.*;

public class Solution {
	 static int MOD = 998244353;

    private static int factorial(int n) {
        int ans = 1;
        for (int i = 1; i <= n; i++) {
            ans = (int) ((long) ans * i % MOD);
        }
        return ans;
    }
	public static void main (String[] args) throws java.lang.Exception {
	    // Write your code here
        // Take input and print desired output
		 Scanner scanner = new Scanner(System.in);
        int t = scanner.nextInt();
        while (t-- > 0) {
            int p = scanner.nextInt();
            int q = scanner.nextInt();
            int r = scanner.nextInt();
            int[][][] dp = new int[p + 1][q + 1][r + 1];
            for (int i = 0; i < =p; i++) {
                for (int j = 0; j <= q; j++) {
                    for (int k = 0; k <= r; k++) {
                        if (i + j < k) {
                            dp[i][j][k] = 0;
                        } else if (i + j == k) {
                            dp[i][j][k] = factorial(i + j);
                        } else if (j == 1) {
                            dp[i][j][k] = 0;
                        } else if (k == 1) {
                            dp[i][j][k] = 1;
                        } else {
                            dp[i][j][k] = (int) (((long) i * dp[i - 1][j][k - 1] + (long) j * dp[i][j - 1][k - 1])
                                    % MOD);
                        }
                    }
                }
            }
            System.out.println(dp[p][q][r]);
        }
	
	}
}

私が試したこと:

import java.util.*;
import java.lang.*;
import java.io.*;

public class Solution {
	 static int MOD = 998244353;

    private static int factorial(int n) {
        int ans = 1;
        for (int i = 1; i <= n; i++) {
            ans = (int) ((long) ans * i % MOD);
        }
        return ans;
    }
	public static void main (String[] args) throws java.lang.Exception {
	    // Write your code here
        // Take input and print desired output
		 Scanner scanner = new Scanner(System.in);
        int t = scanner.nextInt();
        while (t-- > 0) {
            int p = scanner.nextInt();
            int q = scanner.nextInt();
            int r = scanner.nextInt();
            int[][][] dp = new int[p + 1][q + 1][r + 1];
            for (int i = 0; i < =p; i++) {
                for (int j = 0; j <= q; j++) {
                    for (int k = 0; k <= r; k++) {
                        if (i + j < k) {
                            dp[i][j][k] = 0;
                        } else if (i + j == k) {
                            dp[i][j][k] = factorial(i + j);
                        } else if (j == 1) {
                            dp[i][j][k] = 0;
                        } else if (k == 1) {
                            dp[i][j][k] = 1;
                        } else {
                            dp[i][j][k] = (int) (((long) i * dp[i - 1][j][k - 1] + (long) j * dp[i][j - 1][k - 1])
                                    % MOD);
                        }
                    }
                }
            }
            System.out.println(dp[p][q][r]);
        }
	
	}
}

解決策 1

for ループは 0 から始まり N まで実行されますが、これは問題ありません。これは主に、配列のすべての次元で要素を 1 つ大きくして、配列にすべてのインデックスを含めるためです。

ただし、負のインデックスが含まれていないため、これらのループを初めて通過するとき、このコードは負のアドレス指定された要素にアクセスしようとし、範囲外エラーで失敗します。

dp[i][j][k] = (int) (((long) i * dp[i - 1][j][k - 1] + (long) j * dp[i][j - 1][k - 1]

デバッガーを 30 秒使用すれば、それがわかるでしょう。

注意してください: 階乗値はすぐに非常に大きくなります: 12! は 32 ビット整数に収まる最大値であるため、このコードでは簡単に奇妙な結果が得られる可能性があります。

dp[i][j][k] = factorial(i + j);

解決策 2

引用:

DP[i][j][k] = (int) (((long) i * dp[i – 1][j][k – 1] + (長い) j * dp[i][j – 1][k – 1])
% モッド);

上記の行が原因である可能性があります。 i (また j、 また k) は 0。 ループはゼロから開始する必要がありますか (ループはゼロから開始すべきではありませんか) 1?)?

コメント

タイトルとURLをコピーしました