Pagini recente » Cod sursa (job #1330178) | Cod sursa (job #1290592) | Cod sursa (job #293609) | Cod sursa (job #20135) | Cod sursa (job #1580714)
#include <bits/stdc++.h>
using namespace std;
const int md = 3210121, SMAX = 1 << 14, KMAX = 32;
int c[SMAX][KMAX], a[KMAX][KMAX];
int part[SMAX][KMAX];
int k, s, n;
int act[1 << 20][KMAX];
void citire() {
ifstream fin("cowfood.in");
fin >> k >> s >> n;
for(int i = 0; i < n; ++i)
for(int j = 0; j < k; ++j)
fin >> a[i][j];
}
void add(int &a, int b) {
a += b;
if(a >= md)
a %= md;
else if(a < 0)
for(; a < 0; a += md);
}
int ways(int suma, int cate) {
return c[suma + cate - 1][cate - 1];
}
void precalc() {
for(int i = 0; i < SMAX; ++i)
c[i][0] = 1;
for(int i = 1; i < SMAX; ++i)
for(int j = 1; j < KMAX; ++j)
add(c[i][j], c[i - 1][j] + c[i - 1][j - 1]);
for(int i = 0; i < SMAX; ++i)
for(int j = 1; j < KMAX; ++j)
part[i][j] = ways(i, j);
for(int i = 1; i < SMAX; ++i)
for(int j = 0; j < KMAX; ++j)
add(part[i][j], part[i - 1][j]);
}
int rasp(int snow) {
if(snow < 0) return 0;
int Ret = part[snow][k];
return Ret;
}
void solve() {
int Ret = 0;
for(int i = 2; i <= s; ++i)
add(Ret, ways(i, k) - k);
for(int i = 0; i < n; ++i)
memcpy(act[1 << i], a[i], sizeof(act[1 << i]));
for(int i = 1; i < 1 << n; ++i)
for(int j=0;j<n;++j)
if(i&(1<<j))
for(int ult = 0; ult < k; ++ult)
act[i][ult] = max(act[i][ult], act[i ^ (1 << j)][ult]);
for(int i=1;i<1<<n;++i){
int sum=0;
for(int j=0;j<k;++j)
add(sum,act[i][j]);
int crt=__builtin_popcount(i);
sum=rasp(s-sum);
if(crt & 1)
add(Ret,-sum);
else add(Ret,sum);
}
ofstream("cowfood.out") << Ret;
}
int main() {
citire();
precalc();
solve();
}