ゴールドコインパイ

リンク:https
://ac.nowcoder.com/acm/contest/11371/E出典:Niuke

タイトルの説明
最近、牛は金のコインを小麦粉で包み、パイに焼くことに熱心です。i番目のパイにはNi(1 <= Ni <= 25)の金貨が含まれており、この番号はパイの表面にはっきりとマークされています。
牛は、草の上に焼き上げたすべてのパイを、R行(1 <= R <= 100)とC列(1 <= C <= 100)のマトリックスに配置しました。あなたは座標(1,1)でパイの隣に立っています。もちろん、あなたはそのパイのすべての金貨を手に入れることができます。現在の位置から草の反対側まで歩き、座標(R、C)でパイの横で停止する必要があります。移動するたびに、次の列のパイに移動する必要があります。行数は1を超えて変更することはできません(つまり、座標(r、c)でパイの隣に立っている場合、次に、座標(r-1、c + 1)、(r、c + 1)、または(r + 1、c + 1))を使用してパイまで歩くことができます。パイを通り過ぎると、パイの中のすべての金貨を取り除くことができます。もちろん、草を半分残して便利なゴールドコインを失いたくないでしょうが、最終的には座標(R、C)のパイの横で停止する必要があります。
これで、パイマトリックスの各パイのゴールドコインの数がマークされたテーブルができました。それで、規則によれば、あなたはせいぜいどれくらいの金を手に入れることができますか?
たとえば、牛はパイを次のマトリックスに配置し、マトリックス内の数字は、その位置にあるパイ内の金貨の数を示します。

始点-> 6 5 3 7 9 2 7
2 4 3 5 6 8 6
4 9 9 9 1 5 8 <-終点
以下は合法的なルートです。

始点-> 6 5 3 7 9 2 7

2 4 3 5 6 8 6
\ /
4 9 9-9 1 5-8 <-終点は
上記のルートたどることで、合計6 + 4 + 9 + 9 +6を得ることができます+ 5 + 8 = 47ゴールドコイン。ルールに従って、このマトリックスで最大50個のゴールドコインを取得できます。ルートを次の図に示します。

始点-> 6 5 3 7 9 2 7

2 4 3 5 6-8 6
\ /
4 9 9-9 1 5 8 <-終点
(モノスペースフォントで表示するには、メモ帳にコピーしてください)

入力の説明:
行1:スペースで区切られた2つの整数、RとC
行2 ... R + 1:各行には、スペースで区切られたCの正の整数が含まれ、行の左から右への各塗りつぶしを示しますパイ内のゴールドコインの数
出力の説明:
1行目:正の整数を出力し、収集できるゴールドコインの最大数を示します。
例1
入力
コピー
3 7
6 5 3 7 9 2 7
2 4 3 5 6 8 6
4 9 9 9 1 58
出力
コピー
50

単純なdp、注意すべき重要なことは、左から右への列挙の順序であり、一部の位置は歩くことができません。

#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <set>
#include <string>
#include <queue>
#include <map>
#include <stack>
#include <map>
#include <unordered_map>
#include <vector>
#include <cmath>
#include <ext/rope>
#include <bits/stdc++.h> 

using namespace std;

#define gt(x) x = read()
#define int long long

const int mod = 1e9 + 7;

inline int read(int out = 0)
{
    
    
    char c;
    while((c=getchar()) < 48 || c > 57);
    while(c >= 48 && c <= 57) out=out*10+c-48,c=getchar();
    return out; 
}

const int N = 110;
const int M = 1e6 + 10;

int n, m;
int a[N][N];
int f[N][N];

signed main(){
    
    
	ios::sync_with_stdio(false);
	cin.tie();
	cout.tie();
	
	gt(n), gt(m);
	
	for (int i = 1; i <= n; i ++){
    
    
		for (int j = 1; j <= m; j ++)
		  gt(a[i][j]);
	}
	
	f[1][1] = a[1][1];
	for (int i = 2; i <= n; i ++)   f[i][1] = 0;
	for (int j = 2; j <= m; j ++){
    
    
		for (int i = 1; i <= j; i ++){
    
    
			f[i][j] = max(f[i][j], f[i - 1][j - 1] + a[i][j]);
			f[i][j] = max(f[i][j], f[i + 1][j - 1] + a[i][j]);
			f[i][j] = max(f[i][j], f[i][j - 1] + a[i][j]);
		//	cout << i << " " << j << " " << f[i][j] << endl;
		}
	}
	
	cout << f[n][m] << endl;
	
	return 0;
}

おすすめ

転載: blog.csdn.net/qq_45772483/article/details/112639904