3 条题解

  • -10
    @ 2024-7-2 12:46:12

    字典序最大路径

    思路

    本题要求找到一个字典序最大的路径,可以证明答案一定是有限的或者是由某个长度有限的字符串 SSSS 不断重复得到的。

    我们可以使用动态规划来解决这个问题。我们定义 dp[i][j]dp[i][j] 表示从位置 (i,j)(i, j) 出发,所能得到的字典序最大的路径。

    对于每个位置 (i,j)(i, j),我们可以枚举其四个方向,如果该方向存在且没有障碍,则更新 dp[i][j]dp[i][j] 为该方向的 dpdp 值加上当前位置的字符。

    最后,我们从所有非障碍格出发,找到字典序最大的 dpdp 值,即为答案。

    解题方法

    初始化 dpdp 数组,所有位置的值都设置为 1-1

    从所有非障碍格出发,进行动态规划。

    对于每个位置 (i,j)(i, j),枚举其四个方向,如果该方向存在且没有障碍,则更新 dp[i][j]dp[i][j] 为该方向的 dpdp 值加上当前位置的字符。

    找到所有 dpdp 值中字典序最大的值,即为答案。

    复杂度

    时间复杂度:

    𝑂(𝑛×𝑚)𝑂(𝑛×𝑚)

    空间复杂度:

    O(n×m)O(n×m)

    Code

    #include <iostream>
    #include <algorithm>
    #include <string>
    
    using namespace std;
    
    const int MAXN = 1005;
    
    char grid[MAXN][MAXN];
    string dp[MAXN][MAXN];
    int n, m;
    
    int main() {
        cin >> n >> m;
        for (int i = 1; i <= n; i++) {
            cin >> grid[i] + 1;
        }
    
        // 初始化 dp 数组
        for (int i = 1; i <= n; i++) {
            for (int j = 1; j <= m; j++) {
                dp[i][j] = "-1";
            }
        }
    
        // 动态规划
        for (int i = 1; i <= n; i++) {
            for (int j = 1; j <= m; j++) {
                if (grid[i][j] == '#') continue;
    
                // 枚举四个方向
                if (i > 1 && grid[i - 1][j] != '#') {
                    dp[i][j] = max(dp[i][j], dp[i - 1][j] + grid[i][j]);
                }
                if (i < n && grid[i + 1][j] != '#') {
                    dp[i][j] = max(dp[i][j], dp[i + 1][j] + grid[i][j]);
                }
                if (j > 1 && grid[i][j - 1] != '#') {
                    dp[i][j] = max(dp[i][j], dp[i][j - 1] + grid[i][j]);
                }
                if (j < m && grid[i][j + 1] != '#') {
                    dp[i][j] = max(dp[i][j], dp[i][j + 1] + grid[i][j]);
                }
            }
        }
    
        // 找到字典序最大的 dp 值
        string ans = "-1";
        for (int i = 1; i <= n; i++) {
            for (int j = 1; j <= m; j++) {
                if (grid[i][j] != '#' && dp[i][j] > ans) {
                    ans = dp[i][j];
                }
            }
        }
    
        cout << ans << endl;
    
        return 0;//好习惯
    }
    

    最后,本蒟蒻是第一次写题解呦,请大佬们多包涵哟。

    • @ 2024-7-9 18:15:15

      第一次写题解能写错题,你是好样的

    • @ 2024-7-13 18:21:38

      这不是 Luogu P10677 吗

    • @ 2024-10-25 21:46:32

      错的!

信息

ID
4
时间
3000ms
内存
1024MiB
难度
7
标签
递交数
139
已通过
25
上传者