动态规划-1620. 收集硬币

感情迁移 提交于 2020-04-08 08:47:49

2020-04-08 07:45:18

问题描述:

给定一个n * m个的矩阵,矩阵的每个位置有一定数量的硬币,你从(0,0)位置出发,每次只能往右或者往下走,当他经过某个格子的时候,可以得到这个格子上的所有硬币,当它走到第(n-1,M-1)位置时游戏结束,在游戏开始前,你有ķ次机会,可以交换某两个格子中的硬币数量中,k次机会不一定要使用完,求从(0,0)走到第(n-1,M-1)所能得到的最大的硬币数量。

样例

输入:
matrix = [[9,9,9,0,0],[0,0,9,0,0],[0,0,0,0,0],[0,0,9,0,0],[9,0,9,9,9]]
k = 1
输出:81

注意事项

  • 2≤n,m≤50
  • 0<=k<=20
  • 0<=matrix[I][j]<=1000000

问题求解:

    int nums[55];
    int dp[55][55][25][25];
    int collectingCoins(vector<vector<int>> &matrix, int k) {
        // Write your code here
        int n = matrix.size();
        int m = matrix[0].size();
        memset(dp, -0x3f,sizeof(dp));
        dp[0][0][0][0] = matrix[0][0], dp[0][0][0][1] = 0;
        for(int x = 0; x < n; x++) {
            for(int y = 0; y < m; y++) {
                if (x == 0 && y == 0) continue;
                int idx = 0;
                if(x) {
                    for(int j = y + 1; j < m; j++) {
                        nums[idx++] = matrix[x - 1][j];
                    }
                }
                for(int j = 0; j < y; j++) {
                    nums[idx++] = matrix[x][j];
                }
                sort(nums,nums + idx,greater<int>());
                for(int used = 0; used <= k;used ++)
                {
                    for(int blank = 0;blank <= x + y + 1 && blank <= k; blank++)
                    {
                        int res = INT_MIN;
                        if(x) {
                            res = max(res, dp[x - 1][y][used][blank] + matrix[x][y]);
                            if(blank) 
                            {
                                res = max(res,dp[x - 1][y][used][blank - 1]);
                            }
                            int sum = 0;
                            int it = 0;
                            for(int cntuse = 1;cntuse <= used && cntuse <= idx;cntuse ++)
                            {
                                sum += nums[it++];
                                res = max(res,dp[x - 1][y][used - cntuse][blank] + matrix[x][y] + sum);
                                if(blank) 
                                {
                                    res = max(res,dp[x - 1][y][used - cntuse][blank - 1] + sum);
                                }
                            }
                        }
                        if(y)
                        {
                            res = max(res,dp[x][y - 1][used][blank] + matrix[x][y]);
                            if(blank) 
                            {
                                res = max(res,dp[x][y - 1][used][blank - 1]);
                            }
                        }
                        dp[x][y][used][blank] = res;
                    }
                }
            }
        }
        int res = 0;
        for(int i = 0;i <= k; i++) {
            res = max(res,dp[n - 1][m - 1][i][i]);
        }
        return res;
    }

  

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!