Pagini recente » Cod sursa (job #2020825) | Cod sursa (job #2353963) | Cod sursa (job #2445625) | Cod sursa (job #304589) | Cod sursa (job #873358)
Cod sursa(job #873358)
#include <cstdio>
#include <algorithm>
using namespace std;
int dp[31][10000];
int exp[21][31];
int mod = 3210121;
inline int cate(int N, int S) {
if (S < 0) return 0;
if (N == 1) return S + 1;
return dp[N][S];
if (dp[N][S]) return dp[N][S];
dp[N][S] = 0;
for (int i = 0; i <= S; ++i)
dp[N][S] = (dp[N][S] + cate(N-1, S - i)) % mod;
return dp[N][S];
}
int main() {
freopen("cowfood.in", "r", stdin);
freopen("cowfood.out", "w", stdout);
int K, S, N;
scanf("%d %d %d", &K, &S, &N);
for (int i = 1; i <= N; ++i)
for (int j = 1; j <= K; ++j) scanf("%d", &exp[i][j]);
for (int i = 0; i <= S; ++i) dp[1][i] = i + 1;
for (int i = 1; i < K; ++i) {
dp[i+1][0] = dp[i][0];
int total = dp[i][0];
for (int j = 1; j <= S; ++j) {
total += dp[i][j];
while (total > mod) total -= mod;
dp[i+1][j] += total;
while (dp[i+1][j] > mod) dp[i+1][j] -= mod;
}
}
int ret = cate(K, S);
for (int mask = 1; mask < (1 << N); ++mask) {
int semn = 1;
if (__builtin_popcount(mask) % 2) semn = -1;
int T = S;
int mx[K+1];
for (int i = 1; i <= K; ++i) mx[i] = 0;
for (int j = 0; j < N; ++j) if (mask & (1<<j)) {
for (int i = 1; i <= K; ++i) mx[i] = max(mx[i], exp[j+1][i]);
}
for (int i = 1; i <= K; ++i) {
T -= mx[i];
}
ret += semn * cate(K, T);
while (ret < 0) ret += mod;
while (ret >= mod) ret -= mod;
}
// 1 singur nul.
ret -= K * S;//cate(K - 1, S - K + 1) * K;
ret--;
while (ret < 0) ret += mod;
printf("%d\n", ret);
return 0;
}