题目
你要开发一座金矿,地质勘测学家已经探明了这座金矿中的资源分布,并用大小为 m * n 的网格 grid 进行了标注。每个单元格中的整数就表示这一单元格中的黄金数量;如果该单元格是空的,那么就是 0。
为了使收益最大化,矿工需要按以下规则来开采黄金:
- 每当矿工进入一个单元,就会收集该单元格中的所有黄金。
- 矿工每次可以从当前位置向上下左右四个方向走。
- 每个单元格只能被开采(进入)一次。
- 不得开采(进入)黄金数目为 0 的单元格。
- 矿工可以从网格中 任意一个 有黄金的单元格出发或者是停止。
示例 1:
输入:grid = [[0,6,0],[5,8,7],[0,9,0]] 输出:24 解释: [[0,6,0], [5,8,7], [0,9,0]] 一种收集最多黄金的路线是:9 -> 8 -> 7。 • 1 • 2 • 3 • 4 • 5 • 6 • 7
示例 2:
输入:grid = [[1,0,7],[2,0,6],[3,4,5],[0,3,0],[9,0,20]] 输出:28 解释: [[1,0,7], [2,0,6], [3,4,5], [0,3,0], [9,0,20]] 一种收集最多黄金的路线是:1 -> 2 -> 3 -> 4 -> 5 -> 6 -> 7。 • 1 • 2 • 3 • 4 • 5 • 6 • 7 • 8 • 9
解题
方法一:回溯
写法一:
将sum作为参数进行传参(由于局部变量的关系,自动起到回溯的效果)
class Solution { public: int res=0; vector<vector<int>> dirs={{-1,0},{1,0},{0,1},{0,-1}}; int getMaximumGold(vector<vector<int>>& grid) { int m=grid.size(); int n=grid[0].size(); vector<vector<bool>> visit(m,vector<bool>(n,false)); for(int i=0;i<m;i++){ for(int j=0;j<n;j++){ if(grid[i][j]!=0){ visit[i][j]=true; backtracing(grid,visit,grid[i][j],i,j); visit[i][j]=false; } } } return res; } void backtracing(vector<vector<int>>& grid,vector<vector<bool>>& visit,int sum,int x,int y){ res=max(res,sum); for(vector<int>& dir:dirs){ int nx=x+dir[0]; int ny=y+dir[1]; if(nx<0||nx>=grid.size()||ny<0||ny>=grid[0].size()||visit[nx][ny]==true||grid[nx][ny]==0) continue; visit[nx][ny]=true; backtracing(grid,visit,sum+grid[nx][ny],nx,ny); visit[nx][ny]=false; } } }; • 1 • 2 • 3 • 4 • 5 • 6 • 7 • 8 • 9 • 10 • 11 • 12 • 13 • 14 • 15 • 16 • 17 • 18 • 19 • 20 • 21 • 22 • 23 • 24 • 25 • 26 • 27 • 28 • 29 • 30 • 31
写法二
另外声明一个变量path作为过程,不进行传参,要手动+或-
class Solution { public: int res=0; int path=0; vector<vector<int>> dirs={{-1,0},{1,0},{0,1},{0,-1}}; int getMaximumGold(vector<vector<int>>& grid) { int m=grid.size(); int n=grid[0].size(); vector<vector<bool>> visit(m,vector<bool>(n,false)); for(int i=0;i<m;i++){ for(int j=0;j<n;j++){ if(grid[i][j]!=0){ path=grid[i][j]; res=max(path,res);//注意一定要单独比较,否则如果都是单独的起始点,就会失败 visit[i][j]=true; backtracing(grid,visit,i,j); visit[i][j]=false; } } } return res; } void backtracing(vector<vector<int>>& grid,vector<vector<bool>>& visit,int x,int y){ for(vector<int>& dir:dirs){ int nx=x+dir[0]; int ny=y+dir[1]; if(nx<0||nx>=grid.size()||ny<0||ny>=grid[0].size()||visit[nx][ny]==true||grid[nx][ny]==0) continue; path+=grid[nx][ny]; res=max(res,path); visit[nx][ny]=true; backtracing(grid,visit,nx,ny); visit[nx][ny]=false; path-=grid[nx][ny]; } } }; • 1 • 2 • 3 • 4 • 5 • 6 • 7 • 8 • 9 • 10 • 11 • 12 • 13 • 14 • 15 • 16 • 17 • 18 • 19 • 20 • 21 • 22 • 23 • 24 • 25 • 26 • 27 • 28 • 29 • 30 • 31 • 32 • 33 • 34 • 35 • 36