時間限制: 1 s 空間限制: 128000 KB 題目等級 : 鑽石 Diamond 題解 查看運行結果 時間限制: 1 s 空間限制: 128000 KB 題目等級 : 鑽石 Diamond 時間限制: 1 s 空間限制: 128000 KB 題目等級 : 鑽石 Diamond 時間限制: 1 ...
時間限制: 1 s 空間限制: 128000 KB 題目等級 : 鑽石 Diamond 題目描述 Description
菜菜看到了一個游戲,叫做方格游戲~
游戲規則是這樣的:
在一個n*n的格子中,在每個1*1的格子里都能獲得一定數量的積分獎勵,記左上角為(1,1),右下角為(n,n)。游戲者需要選擇一條(1,1)到(n,n)的路徑,並獲得路徑上獎勵的積分。對於路徑當然也有要求啦,要求是只能往坐標變大的方向走【從(x,y)到(x+1,y)或者(x,y+1)】,走過2n-1個區域到達(n,n)。當然,獲得的積分最高的就能取勝啦。
這時,菜菜看到了他的好友月月,於是邀請她來玩雙人版的。雙人版的規則就是在單人版的基礎上加上一條兩人的路線不能相同。月月知道菜菜的很聰明,怕輸得太慘,就不太願意和他玩。菜菜可慌了,於是定義了一個公平值D,這個公平值等於倆人所選擇的路徑所能獲得的積分一一對應相減的差的絕對值之和,即D=sigma (|kxi-kyi|)|(kx,ky分別為菜菜,月月走過的每一個區域的叢林繫數)。不過這可是個龐大的計算任務,菜菜找到了你,請你幫忙計算公平值的最大值。
輸入描述 Input Description第一行,一個正整數n
接下來的n行,每行n個整數,表示叢林中每個區域的公平值
輸出描述 Output Description一個整數Dmax,即公平值的最大值
樣例輸入 Sample Input4
1 2 3 4
1 5 3 2
8 1 3 4
3 2 1 5
樣例輸出 Sample Output13
數據範圍及提示 Data Size & Hint對於20%的數據,保證0<n≤20
對於50%的數據,保證0<n≤50
對於100%的數據,保證0<n≤100且對於所有的i,j保證|Kij|≤300
首先這題四維會爆空間。
所以就學了一下用三維表示。
前提:
1.設兩個人的坐標分別為A,B;
2.n*n的方格,從(1,1)點到(n,n)點需要的總步數為2*n+1(n個橫,n個列,其中有一個重覆)
我們用k來表示步數
我們用i來表示在第k步A的橫坐標為i
用j來表示在第k步B的橫坐標為j
那麼A的坐標可以表示為(i,k-i+1)
B的坐標可以表示為(j,k-j+1)
對於每一個點(i,j)
同樣有四中情況轉移而來
1.A從上到下 dp[i-1][j][k-1]
2.B從上到下 dp[i][j-1][k-1]
3.AB同時從上到下dp[i-1][j-1][k-1]
4.AB同時從左往右dp[i][j][k-1]
然後再加上這個點的值就好
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<cmath> 5 #include<cstdlib> 6 using namespace std; 7 void read(int &n) 8 { 9 char c='+';int x=0;bool flag=0; 10 while(c<'0'||c>'9') 11 {c=getchar();if(c=='-')flag=1;} 12 while(c>='0'&&c<='9') 13 {x=x*10+(c-48);c=getchar();} 14 flag==1?n=-x:n=x; 15 } 16 int n; 17 int dp[101][101][301]; 18 int a[101][101]; 19 int ans=0; 20 int main() 21 { 22 read(n); 23 for(int i=1;i<=n;i++) 24 for(int j=1;j<=n;j++) 25 read(a[i][j]); 26 // a :(i,k-i+1) 27 // b :(j,k-j+1) 28 for(int k=1;k<=2*n-1;k++) 29 { 30 for(int i=1;i<=n&&i<=k;i++) 31 for(int j=1;j<=n&&j<=k;j++) 32 { 33 dp[i][j][k]=max(dp[i-1][j][k-1],dp[i][j][k]); 34 dp[i][j][k]=max(dp[i][j-1][k-1],dp[i][j][k]); 35 dp[i][j][k]=max(dp[i-1][j-1][k-1],dp[i][j][k]); 36 dp[i][j][k]=max(dp[i][j][k-1],dp[i][j][k]); 37 dp[i][j][k]+=abs(a[i][k-i+1]-a[j][k-j+1]); 38 } 39 } 40 printf("%d",dp[n][n][2*n-1]); 41 return 0; 42 }