找来回拿的最多的价值是多少,也就是俩个人从起点开始,一起走最后到终点的最大价值;
dp【i】【j】【k】i为第一个人的横坐标;j为第二个人的横坐标;k为走的步数
这样也就能算出纵坐标
从而得到4个转移方程分别为 右下 下右 右右 下下
#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
#define ll long long
ll dp[105][105][300];
ll map1[200][200];
int main()
{
int n;
while(~scanf("%d",&n))
{
memset(map1,0,sizeof(map1));
for(int i=0; i<=n; i++)
for(int j=0; j<=n; j++)
for(int k=0; k<=2*n-2; k++)
dp[i][j][k]=-1e18;
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
scanf("%I64d",&map1[i][j]);
}
}
dp[1][1][0]=map1[1][1];
for(int k=1;k<=n*2-2;k++)
{
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
ll val;
int x1,x2,y1,y2;
x1=i,x2=j,y1=k-x1+2,y2=k-x2+2;
if(y1<1||y1>n||y2<1||y2>n)continue;
if(x1==x2&&y1==y2)
val=map1[x1][y1];
else val=map1[x1][y1]+map1[x2][y2];
dp[x1][x2][k]=max(dp[x1-1][x2][k-1]+val,dp[x1][x2][k]);
dp[x1][x2][k]=max(dp[x1][x2-1][k-1]+val,dp[x1][x2][k]);
dp[x1][x2][k]=max(dp[x1-1][x2-1][k-1]+val,dp[x1][x2][k]);
dp[x1][x2][k]=max(dp[x1][x2][k-1]+val,dp[x1][x2][k]); //printf("ok");
}
}
}
printf("%I64d\n",dp[n][n][2*n-2]);
}
}