<p>You have <code>n</code> dice, and each dice has <code>k</code> faces numbered from <code>1</code> to <code>k</code>.</p>

<p>Given three integers <code>n</code>, <code>k</code>, and <code>target</code>, return <em>the number of possible ways (out of the </em><code>k<sup>n</sup></code><em> total ways) </em><em>to roll the dice, so the sum of the face-up numbers equals </em><code>target</code>. Since the answer may be too large, return it <strong>modulo</strong> <code>10<sup>9</sup> + 7</code>.</p>

<p>&nbsp;</p>
<p><strong class="example">Example 1:</strong></p>

<pre>
<strong>Input:</strong> n = 1, k = 6, target = 3
<strong>Output:</strong> 1
<strong>Explanation:</strong> You throw one die with 6 faces.
There is only one way to get a sum of 3.
</pre>

<p><strong class="example">Example 2:</strong></p>

<pre>
<strong>Input:</strong> n = 2, k = 6, target = 7
<strong>Output:</strong> 6
<strong>Explanation:</strong> You throw two dice, each with 6 faces.
There are 6 ways to get a sum of 7: 1+6, 2+5, 3+4, 4+3, 5+2, 6+1.
</pre>

<p><strong class="example">Example 3:</strong></p>

<pre>
<strong>Input:</strong> n = 30, k = 30, target = 500
<strong>Output:</strong> 222616187
<strong>Explanation:</strong> The answer must be returned modulo 10<sup>9</sup> + 7.
</pre>

<p>&nbsp;</p>
<p><strong>Constraints:</strong></p>

<ul>
	<li><code>1 &lt;= n, k &lt;= 30</code></li>
	<li><code>1 &lt;= target &lt;= 1000</code></li>
</ul>

class Solution:
    def numRollsToTarget(self, n: int, k: int, target: int) -> int:
        '''
        target need to be in the range[n*1, n*k]
        dp[i][j] := number of possible ways
        i := use first n dices
        j := sum up to j
        for k in range(1,k+1):
            dp[i+1][j] = (dp[i][j] + dp[i][j-k])%MOD
        optimization: space
        # '''
        # if not (n <= target <= n * k):
        #     return 0  # 无法组成 target
        # MOD = 10 ** 9 + 7
        # dp = [[0]*(target+1-n) for _ in range(n+1)]
        # dp[0][0] = 1
        # for i in range(n):
        #     for j in range(target-n+1):
        #         for x in range(min(k,j+1)):# 掷出了 x
        #             dp[i+1][j] = (dp[i+1][j] + dp[i][j-x])%MOD
        # return dp[-1][-1]

        if not (n <= target <= n * k):
            return 0  # 无法组成 target
        MOD = 10 ** 9 + 7
        dp = [0] * (target + 1 - n)
        dp[0] = 1
        
        for i in range(n):
            new_dp = [0] * (target + 1 - n)
            for j in range(target - n + 1):
                for x in range(min(k, j + 1)):  # 掷出了 x
                    new_dp[j] = (new_dp[j] + dp[j - x]) % MOD
            dp = new_dp
        
        return dp[-1]

16500