/*
solution:
dp
设dp[i][j][x][y]:=走到i,j处,手中有x件宝物,且最近拿的一件宝物的价值为y的方案数
note:
宝物价值可能为0,所以要加上1.
*/
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn = 55;
const int M = 1000000007;
typedef long long ll;
ll dp[maxn][maxn][15][15];
int n, m, k; //n行m列
int c[maxn][maxn];
int main()
{
//freopen("in.txt", "r", stdin);
scanf("%d%d%d", &n, &m, &k);
memset(dp, 0, sizeof(dp));
memset(c, 0, sizeof(c));
for(int i = 0; i < n; i++) {
for(int j = 0; j < m; j++) {
scanf("%d", &c[i][j]);
c[i][j]++;
}
}
dp[0][0][1][c[0][0]] = 1;
dp[0][0][0][0] = 1;
for(int i = 0; i < n; i++) {
for(int j = 0; j < m; j++) {
for(int x = 0; x <= k; x++) { //手中宝物个数
for(int y = 0; y <= 13; y++) { //手中宝物最大价值
if(!dp[i][j][x][y]) continue;
//如果向右或者向下的那一格可以拿的话
if(c[i+1][j] > y) {
dp[i+1][j][x+1][c[i+1][j]] += dp[i][j][x][y];
dp[i+1][j][x+1][c[i+1][j]] %= M;
}
if(c[i][j+1] > y) {
dp[i][j+1][x+1][c[i][j+1]] += dp[i][j][x][y];
dp[i][j+1][x+1][c[i][j+1]] %= M;
}
//不拿
dp[i+1][j][x][y] += dp[i][j][x][y];
dp[i+1][j][x][y] %= M;
dp[i][j+1][x][y] += dp[i][j][x][y];
dp[i][j+1][x][y] %= M;
}
}
}
}
ll ans = 0;
for(int i = 0; i <= 13; i++)
ans = (ans + dp[n-1][m-1][k][i]) % M;
cout << ans << endl;
return 0;
}
地宫取宝(dp)
最新推荐文章于 2021-12-12 11:49:19 发布