• P1541


    P1541

    考虑 (DP)

    首先考虑 (DP) 的状态表示:(dp[a][b][c][d]) 表示 走 (1) 格还剩 (a) 个,走 (2) 格还剩 (b) 个,走 (3) 格还剩 (c) 个,走 (4) 个还剩 (d) 个最大的权值和。

    那么在当前状态下在还能走的情况下可以走一格,两格,三格,四格。

    所以考虑记忆化搜索,思维难度较小。

    (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)

    当前的所在位置是 int pos = 1 + (a0 - a) + (a1 - b) * 2 + (a2 - c) * 3 + (a3 - d) * 4;

    最终算出答案。

    我的代码有点妖娆,大概思路就是不累加当前所在位置的权值,而是算下一个能够到达的位置的权值,这样算就少算了开始的第一个位置的值,最后要加上去。

    #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;
    }
    
    
  • 相关阅读:
    liunx下mysql数据库使用之三范式,关系模型设计注意项,安装目录结构
    Liunx系统学习一,liunx系统的目录结构及含义
    liunx环境下的mysql数据库配置文件my.conf内的参数含义
    linux下打开chm文件的方法
    java的四舍五入算法
    【JVM】jvm垃圾回收器相关垃圾回收算法
    Linux下MySQL数据库常用基本操作 一
    liunx环境下安装mysql数据库
    加权平均
    Host绑定
  • 原文地址:https://www.cnblogs.com/strategist-614/p/12521045.html
Copyright © 2020-2023  润新知