简体   繁体   中英

Finding trinomial coefficients using dynamic programming

I'm trying to implement a function to calculate trinomial coefficient in Java using dynamic programming. I'm using the formula:

T(n,k)= 1 if n=0 and k=0
T(n,k)= 0 if k<-n or k>n 
T(n,k)=T(n-1,k-1)+T(n-1,k)+T(n-1,k+1)

I'm using a 2D array to store results of all sub-problems. However, the result I get for a particular n and k is very far from the correct answer. Here is my implementation of the method:

public static long trinomial(int n, int k) {
    if (n == 0 && k == 0) return 1;
    if (k < -n || k > n) return 0;
    long[][] T = new long[n+1][2*n+3];
    T[0][(2*n+3)/2] = 1;
    for (int i = 1; i <= n; i++) {
        for (int j = -i; j <= i; j++) {
            T[i][j+n+1] = T[i-1][j+n] + T[i-1][j+n+1] + T[i-1][j+n+2];
        }
    }
    if (k < 0) return T[n][k+n];
    else return T[n][k];
}

I get T(24,12) = 123286440 . However, the correct answer is: 287134346 . I get T(3,3) = 6 . But the correct answer is 1 . When I computed T(3,3) on a paper using the same method, I get T(3,3) = 1 but in computer I get the wrong answer. There are no compilation errors.

There is a better way to implement the function. The triangle of coefficients for trinomial coefficients will be symmetrical, ie, T(n,k)=T(n,-k). So, the no of columns for the array can be the same as row, ie, n+1. And T(n,-k) can also be computed easily. Here is the implementation:

public static long trinomial(int n, int k) {
    if (n == 0 && k == 0) return 1;
    if (k < -n || k > n) return 0;
    long[][] T = new long[n + 1][n + 1];
    T[0][0] = 1;
    for (int i = 1; i <= n; i++) {
        for (int j = 0; j <= i; j++) {
            if (j == 0) T[i][j] = T[i - 1][j] + 2 * T[i - 1][j + 1];
            else if (j == i) T[i][j] = T[i - 1][j - 1];
            else T[i][j] = T[i - 1][j - 1] + T[i - 1][j] + T[i - 1][j + 1];
        }
    }
    if (k < 0) return T[n][Math.abs(k)];
    else return T[n][k];
}

You can create two methods: one returns a 2d array ie trinomial triangle , and the second returns the specified coefficient from this array. It's more convenient for tests.

public static long trinomialCoefficient(long[][] triangle, int n, int k) {
    return triangle[n][triangle.length - 1 + k];
}
public static long[][] trinomialTriangle(int n) {
    // new array filled with zeros
    long[][] arr = new long[n + 1][2 * n + 1];
    // first entry
    arr[0][n] = 1;
    // iterate over the rows of the array
    // starting from the second
    for (int i = 1; i < arr.length; i++) {
        // iterate over the columns of the array
        for (int j = 0; j < arr[i].length; j++) {
            // each entry is the sum of the three
            // entries above it, if they exist
            arr[i][j] = arr[i - 1][j];
            if (j > 0)
                arr[i][j] += arr[i - 1][j - 1];
            if (j < arr[i].length - 1)
                arr[i][j] += arr[i - 1][j + 1];
        }
    }
    return arr;
}
public static void main(String[] args) {
    long[][] arr = trinomialTriangle(7);

    // output
    System.out.println("T(4,0)=" + trinomialCoefficient(arr, 4, 0));
    System.out.println("T(5,-2)=" + trinomialCoefficient(arr, 5, -2));
    System.out.println("T(7,7)=" + trinomialCoefficient(arr, 7, 7));

    // output triangle
    for (int i = 0; i < arr.length; i++) {
        for (int j = 0; j < arr[i].length; j++)
            if (arr[i][j] > 0)
                System.out.printf("%3d ", arr[i][j]);
            else
                System.out.print("    ");
        System.out.println();
    }
}

Output:

T(4,0)=19
T(5,-2)=30
T(7,7)=1
                              1                             
                          1   1   1                         
                      1   2   3   2   1                     
                  1   3   6   7   6   3   1                 
              1   4  10  16  19  16  10   4   1             
          1   5  15  30  45  51  45  30  15   5   1         
      1   6  21  50  90 126 141 126  90  50  21   6   1     
  1   7  28  77 161 266 357 393 357 266 161  77  28   7   1 

See also: Convert negative index to positive index in an array (Trinomial Triangle)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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