312. Burst Balloons

public class Solution {
    public int maxCoins(int[] nums) {
        int n = nums.length;
        int[] newNum = new int[n+2];
        newNum[0] = 1; newNum[n+1] = 1;
        for(int i=0; i<n; i++){
            newNum[i+1] = nums[i];
        }
        
        int[][] memo = new int[n+2][n+2];
        return dfs(newNum, memo, 0, n+1);
    }
    
    public int dfs(int[] nums, int[][] memo, int left, int right){
        if(right - left <= 1) return 0;
        if(memo[left][right] != 0) return memo[left][right];
        int ans = 0;
        for(int i = left+1; i<right; i++){      // 最後一個戳破, i means last brust balloon
            ans = Math.max(ans, dfs(nums, memo, left, i) + dfs(nums, memo, i, right) + nums[left]*nums[i]*nums[right]);
        }
        memo[left][right] = ans;
        return ans;
    }
}
// a balloon does not depend on the balloons already burst
// only the first and last balloons we are sure of their adjacent balloons before hand