1. 程式人生 > >洛谷P2380 狗哥采礦

洛谷P2380 狗哥采礦

sca 子矩陣 data 背景 hold 兩個 esp clu using

P2380 狗哥采礦

題目背景

又是一節平靜的語文課

狗哥閑來無事,出來了這麽一道題

題目描述

一個n*m的矩陣中,每個格子內有兩種礦yeyenum和bloggium,並且知道它們在每個格子內的數量是多少。最北邊有bloggium的收集站,最西邊有 yeyenum 的收集站。現在要你在這些格子上面安裝向北或者向西的傳送帶(每個格子只能裝一種)。問最多能采到多少礦?

輸入輸出格式

輸入格式:

第一行包含兩個整數n,m,( 1 ≤ n ≤ 500, 1 ≤ m ≤ 500)。接下來n行m列,表示每個格子中可以傳送到yeyenum的數量(小於1000),再接下來n行m列,表示每個格子中可以傳送到bloggium的數量。n, m 同時為0結束。

輸出格式:

每組測試數據僅輸出一個數,表示最多能采到的礦。

輸入輸出樣例

輸入樣例#1:
4 4
0 0 10 9 
1 3 10 0
4 2 1 3 
1 1 20 0 
10 0 0 0 
1 1 1 30 
0 0 5 5 
5 10 10 10 
0 0
輸出樣例#1:
98

說明

傳輸過程中不能轉彎,只能走直路。

/*
    我們定義f[i][j]f[i][j]為在以(i,j)(i,j)為右下角的子矩陣中的最大采礦量,由題意我們可知,如果(i,j)(i,j)是向左轉移礦,那麽(i,j-1)(i,j?1),一定也是向左,(i,j-2)(i,j?2)一直到(i,1)(i,1)都是向左,同理如果(i,j)(i,j)是向上轉移礦,那麽(i-1,j)(i?1,j),一定也是向上,(i-2,j)(i?2,j)一直到(1,j)(1,j)都是向左。這就可以其實我們用前綴和去維護一段區間的采礦量。
    在轉移時,我們只關心當前(i,j)(i,j)的采礦方向。設A[i][j]A[i][j]為向上的前綴和,B[i][j]B[i][j]為向左的前綴和,那麽轉移方程f[i][j]=max(f[i-1][j]+B[i][j],f[[i][j-1]+A[i][j])f[i][j]=max(f[i?1][j]+B[i][j],f[[i][j?1]+A[i][j]).
*/ #include<iostream> #include<cstdio> #include<cstring> using namespace std; #define maxn 510 int n,m,a[maxn][maxn],b[maxn][maxn],f[maxn][maxn],ans; int main(){ while(1){ scanf("%d%d",&n,&m); if(n==0&&m==0)return 0; memset(f,0,sizeof
(f)); memset(a,0,sizeof(a)); memset(b,0,sizeof(b)); ans=0; int x; for(int i=1;i<=n;i++) for(int j=1;j<=m;j++){ scanf("%d",&x); a[i][j]=a[i][j-1]+x; } for(int i=1;i<=n;i++) for(int j=1;j<=m;j++){ scanf("%d",&x); b[i][j]=b[i-1][j]+x; } for(int i=1;i<=n;i++) for(int j=1;j<=m;j++){ f[i][j]=max(f[i-1][j]+a[i][j],f[i][j-1]+b[i][j]); ans=max(f[i][j],ans); } printf("%d\n",ans); } }

洛谷P2380 狗哥采礦