codevs1169传纸条

这题挺有意思的:传纸条

题目既然要我们找两条不相交的路(从左上到右下,从右下到左上)

并且要使其路上权值之和最大

我们可以等价于什么?

从左上到右下找两条路,同时走到右下,并且其路上权值和最大

假设有两个人在走,第一个人的坐标为(x1,y1),第二个人的坐标为(x2,y2)

因为只能向右或者是向下所以不难得出dp方程式

dp[x1,y1,x2,y2]=max(dp[x1-1,y1,x2-1,y2],dp[x1-1,y1,x2,y2-1],dp[x1,y1-1,x2-1,y2],dp[x1,y1-1,x2,y2-1])+G[x1][y1]+G[x2][y2];

可以看到这个方程式相当简单粗暴

for嵌套了四个,但还有一个细节是需要注意的,就是当他们走到了同一个点

这种情况是拒绝出现的

(为什么?答案:曼哈顿距离)

曼哈顿距离说明了只有两个人走到同一个点才可能发生路线交叉

所以我们只要特判一下

if(x1==x2 and y1==2)
 continue;

  就行了

时间复杂度O(n^4)

后来听说还有一种方法可以改进为n^3

我就百度了一下,下面引用一下别人家的思想,看看就差不多了

因为 两个人是同时走的所以 每次都是同时移动一格:因此有   x1+y1==x2+y2 == k

则状态方程可以改为:

f(k,x1,x2) = max{  f(k-1,x1,x2),  f(k-1,x-1,x2) ,f(k-1,x1,x2-1),  f(k-1,x1-1,x2-1)  }  + map[x1][k-x1] + map[x2][k-x2]

for(int i=1;i<=n;i++)
{
  for(int j=1;j<=m;j++)
  {
    for(int k=1;k<=n;k++)
    {
      for(int l=1;l<=m;l++)
      {
        if(i==k && j==l)
          continue;
        maxn=max(dp[i-1][j][k-1][l],dp[i-1][j][k][l-1]);
        maxn=max(maxn,dp[i][j-1][k-1][l]);
        maxn=max(maxn,dp[i][j-1][k][l-1]);
        dp[i][j][k][l]=maxn+G[i][j]+G[k][l];
      }
    }
  }
}

  

最后再说一句,这代码未经测试,错了别怪我 :)

posted @ 2015-11-03 19:38  HELLO----WORLD  阅读(117)  评论(0编辑  收藏  举报