請詳見註解~
import sys
def count_combination(bars: int, blocks: int, MAX: int) -> int: # 每個區塊的 bar 數量必須在範圍: [1, MAX]
# dp[i][j] 表示用前 i 個區塊黑條碼加總等於 j 的方法數
dp = [[0] * (bars + 1) for _ in range(blocks + 1)]
dp[0][0] = 1 # 設定初始 0 該區塊黑條碼加總為 0 的方法數為 1
for i in range(1, blocks + 1): # 遍歷區塊數量 i
for j in range(1, bars + 1): # 遍歷對應可能黑條碼總數量 j
for k in range(1, MAX + 1): # 遍歷第 i 區塊可能的黑條碼數 k
if j >= k: # j 等於 k 的情況代表是要讓 dp 從 j = 0 的結果推遞上來
# if j > k or (j == k and i == 1): # 也可以寫成這樣 只有 i = 1 時 才需要考慮 j - k = 0
dp[i][j] += dp[i - 1][j - k] # 遞推重點: (i - 1) 區塊黑條碼數加總為 j - k,那 i 區塊一定能加總為 j
return dp[blocks][bars]
# while True:
# input_data = input()
# if not input_data: break
for input_data in sys.stdin.readlines(): # 看來要讀到 EOF
n, k, m = map(int, input_data.split()) # n: 總條數, k: 區塊數, m: 區塊條數上限
print(count_combination(n, k, m)) # 把動態規劃實踐在函數中