传纸条(lgP1006)

终于有一道一遍过的题了/kk/kk

发现前几道都很难(总之暂时没想出来)就先把这个写了。

其实这题四维 dp 好像能过,但既然写了就写正解吧...

因为路径正着走和反着走都是一样的,所以问题就是求从左上走到右下两条不重合的最大路径。

在转移途中,因为两个路径的长度都一样,所以枚举横纵坐标的和作为第一维(i),两条路径的横坐标(j,k)作为第2,3维。

然后就可以求出横纵坐标了。

注意 j 要始终小于 k ,不然路径会重合(只要它们横坐标不等,就一定不会经过同一个点,路径也就一定不会重合)。

#include<bits/stdc++.h>
using namespace std;
int m,n,a[51][51],f[101][51][51]; //第一维的数组要开两倍qaq
int main()
{
    scanf("%d%d",&m,&n);
    for(int i=1;i<=m;i++)
    {
        for(int j=1;j<=n;j++)
        { 
            scanf("%d",&a[i][j]);
        }
    }
    for(int i=3;i<=m+n;i++)
    {
        for(int j=1;j<=m && j<=i;j++)
        {
            for(int k=j+1;k<=m && k<=i;k++)
            {
                f[i][j][k]=max(f[i-1][j-1][k],max(f[i-1][j][k],max(f[i-1][j][k-1],f[i-1][j-1][k-1])))+a[j][i-j]+a[k][i-k];
            }
        }
    }
    printf("%d",f[m+n-1][m-1][m]);//因为无论如何都到不了f[m+n][m][m],所以直接把上一步答案输出来就好了。
    return 0;
}

 

posted @ 2020-12-11 21:46  樱雪喵  阅读(121)  评论(0编辑  收藏  举报