考慮 \(DP\)c++
首先考慮 \(DP\) 的狀態表示:\(dp[a][b][c][d]\) 表示 走 \(1\) 格還剩 \(a\) 個,走 \(2\) 格還剩 \(b\) 個,走 \(3\) 格還剩 \(c\) 個,走 \(4\) 個還剩 \(d\) 個最大的權值和。spa
那麼在當前狀態下在還能走的狀況下能夠走一格,兩格,三格,四格。code
因此考慮記憶化搜索,思惟難度較小。ci
\(dp[a][b][c][d] = max(dp[a - 1][b][c][d],dp[a][b - 1][c][d],dp[a][b][c - 1][d],dp[a][b][c][d - 1])\) 同時 \(a \geq 1,b \geq 1,c \geq 1,d \geq 1\)it
當前的所在位置是 int pos = 1 + (a0 - a) + (a1 - b) * 2 + (a2 - c) * 3 + (a3 - d) * 4;
class
最終算出答案。搜索
個人代碼有點妖嬈,大概思路就是不累加當前所在位置的權值,而是算下一個可以到達的位置的權值,這樣算就少算了開始的第一個位置的值,最後要加上去。sort
#include <bits/stdc++.h> #define SZ(X) ((int)(X).size()) #define ALL(X) (X).begin(), (X).end() #define rep(I, N) for (int I = 1; I <= (N); ++I) #define repp(I, N) for (int I = 0; I < (N); ++I) #define FOR(I, A, B) for (int I = (A); I <= (B); ++I) #define FORR(I, A, B) for (int I = (A); I >= (B); I--) #define SORT_UNIQUE(c) (sort(c.begin(), c.end()), c.resize(distance(c.begin(), unique(c.begin(), c.end())))) #define GET_POS(c, x) (lower_bound(c.begin(), c.end(), x) - c.begin()) #define MP make_pair #define PB push_back #define MS0(X) memset((X), 0, sizeof((X))) #define MS1(X) memset((X), -1, sizeof((X))) #define LEN(X) strlen(X) #define F first #define S second using namespace std; const int N = 350 + 5; const int M = 45; const double eps = 1e-7; const int mod = 1e9 + 7; typedef long long LL; typedef unsigned long long ULL; typedef long double LD; typedef pair<int, int> PII; typedef vector<int> VI; typedef vector<LL> VL; typedef vector<PII> VPII; typedef pair<LL, LL> PLL; typedef vector<PLL> VPLL; int ax[N], b[N]; int dp[M][M][M][M]; int a0 = 0, a1 = 0, a2 = 0, a3 = 0; int n, m; int dfs(int a, int b, int c, int d) { if (dp[a][b][c][d] != -1) return dp[a][b][c][d]; int ans = 0; int pos = 1 + (a0 - a) + (a1 - b) * 2 + (a2 - c) * 3 + (a3 - d) * 4;//算位置 if (a >= 1) { ans = max(ans, dfs(a - 1, b, c, d) + ax[pos + 1]);// (a-1,b,c,d)表示位置的權值,下同 } if (b >= 1) ans = max(ans, dfs(a, b - 1, c, d) + ax[pos + 2]); if (c >= 1) ans = max(ans, dfs(a, b, c - 1, d) + ax[pos + 3]); if (d >= 1) ans = max(ans, dfs(a, b, c, d - 1) + ax[pos + 4]); return (dp[a][b][c][d] = ans); } int main() { cin >> n >> m; rep(i, n) cin >> ax[i]; rep(i, m) cin >> b[i]; memset(dp, -1, sizeof dp); rep(i, m) { if (b[i] == 1) a0++; else if (b[i] == 2) a1++; else if (b[i] == 3) a2++; else a3++; } cout << dfs(a0, a1, a2, a3) + ax[1] << endl;//加上第一個位置的值 return 0; }