双线DP , 在郑轻的时候 做过 这种双线DP , 这是多维DP 应该是比较简单的 但是那个 时间复杂度的优化 始终看不懂 . 先附上代码吧 , 等看懂了再来 , 补充一下 解释 .
#include<stdio.h>
#include<string.h>
#include<math.h>
#include<iostream>
#include<algorithm>
#include<queue>
#include<vector>
#include<set>
#include<stack>
#include<string>
#include<sstream>
#include<map>
#include<cctype>
#include<limits.h>
using namespace std;
int map1[55][55],m,n,dp[55][55];
int getMax()
{
int i,j,k;
for(i=1;i<=m+n-1;i++) // 这样的话 下面运行 行列数 之和
{
for(j=m-1;j>=0;j--) // 有几行 向下传送几行 .
{
for(k=m-1;k>j;k--) // 从 低的一行开始 .
{
if(i>=k&&i>=j)
dp[j][k]=max(max(dp[j][k],dp[j-1][k-1]),max(dp[j-1][k],dp[j][k-1]))+map1[j][i-j]+map1[k][i-k];
}
}
}
return dp[m-2][m-1];
}
int main()
{
int N;
scanf("%d",&N); // 案例个数
while(N--)
{
memset(map1,0,sizeof(map1));
memset(dp,0,sizeof(dp));
scanf("%d%d",&m,&n); // 输入 长和宽
int i,j;
for(i=0;i<m;i++)
{
for(j=0;j<n;j++)
{
scanf("%d",&map1[i][j]); // 输入图
}
}
printf("%d
",getMax());
}
return 0;
}