大意:
有n个程序员,每个程序员每写一行代码就会产生(a_i)行bug,每个程序员可以写任意多行代码(996石锤了),问写m行代码最多不超过b个bug的方案数有多少
思路:
完全背包问题,(dp[j][k])代表写了j行代码正好产生k个bug的方案数,转移方程:
(dp[j][k]+=dp[j-1][k-a[i]])
外面套n次循环即可,最后答案是(dp[m][0]+......+dp[m][b])
#include<bits/stdc++.h>
using namespace std;
const int N = 500 + 5;
typedef long long LL;
int n, m, mod,a[N],dp[N][N],b;
int main(){
cin >> n >> m >> b >> mod;
for (int i = 1; i <= n;i++){
cin >> a[i];
}
dp[0][0] = 1;
for (int i = 1; i <= n; i++){
for (int j = 1; j <= m; j++){
for (int k = a[i]; k <= b; k++){
dp[j][k] += dp[j - 1][k - a[i]];
dp[j][k] %= mod;
}
}
}
int res = 0;
for (int i = 0; i <= b;i++){
res += dp[m][i];
res %= mod;
}
cout << res << endl;
return 0;
}