有 k 種學分的課程,第 i 種學分為 `a[i]`,有 `b[i]` 門可選。選課總學分恰為 n,求選法數。課程同學分視為無區別。n ≤ 40, k ≤ 8, a ≤ 8, b ≤ 10。
第 i 類課程的生成函數:`(1 + x^{a[i]} + x^{2a[i]} + ... + x^{b[i]*a[i]})`。
總生成函數 = 所有類別生成函數乘積。
答案 = 乘積中 `x^n` 的係數。
#includeusing namespace std; int c[45], tmp[45]; int a[11], b[11]; int main() { int T; scanf("%d", &T); while (T--) { int n, k; scanf("%d%d", &n, &k); for (int i = 1; i <= k; ++i) scanf("%d%d", &a[i], &b[i]); fill(c, c+n+1, 0); c[0] = 1; for (int i = 1; i <= k; ++i) { fill(tmp, tmp+n+1, 0); for (int j = 0; j <= n; ++j) if (c[j]) for (int k = 0; k <= b[i] && j + k*a[i] <= n; ++k) tmp[j + k*a[i]] += c[j]; copy(tmp, tmp+n+1, c); } printf("%d\n", c[n]); } return 0; }
普通母函數經典入門題。將「有限重複物品選擇」建模為多項式乘法,DP 實現係數計算。掌握此模板,可解決所有「有限重複物品湊目標和方案數」問題。