化简公式然后递推....


#include <bits/stdc++.h>
using namespace std;
typedef long long LL;

const int INF = 0x3f3f3f3f;

int dp[33][33][60 * 33];
int g[33][33], n, m;

void update(int &x, int y)
{
	if(x > y) x = y;
}

void work()
{
	int tot = 0;
	scanf("%d%d", &n, &m);
	for(int i = 1; i <= n; i++)
		for(int j = 1; j <= m; j++)
			scanf("%d", &g[i][j]), tot += g[i][j];
	tot = 59 * 30;
	for(int i = 1; i <= n; i++)
		for(int j = 1; j <= m; j++)
			for(int k = 0; k <= tot; k++)
				dp[i][j][k] = INF;
	
	dp[1][1][g[1][1]] = g[1][1] * g[1][1];
	
	for(int i = 1; i <= n; i++)
		for(int j = 1; j <= m; j++)
			for(int k = 0; k <= tot; k++) {
				if(dp[i][j][k] == INF) continue;
				if(i != n) update(dp[i+1][j][k + g[i+1][j]], dp[i][j][k] + g[i+1][j] * g[i+1][j]);
				if(j != m) update(dp[i][j+1][k + g[i][j+1]], dp[i][j][k] + g[i][j+1] * g[i][j+1]);
			}
	int ans = INF;
	for(int i = 0; i <= tot; i++) if(dp[n][m][i] != INF)
		update(ans, (n + m - 1) * dp[n][m][i] - i * i);
	printf("%d\n", ans);
}

int main()
{
	int _;
	scanf("%d", &_);
	for(int i = 1; i <= _; i++) {
		printf("Case #%d: ", i);
		work();
	}	
	return 0;
}