看完题之后:这啥啊,这么复杂,每一步都有九种可能,还要考虑他的权重
解题思路:本题的重点是如何计算他的路线,所以我想怎么判断,还要结合他的规则(不能后退),反正想了很长时间,感觉很复杂。想一步一步来,判断他是向下走还是向右走合适,如果向右走一格那么就跟原来下面的三格比较,但是逻辑有问题,就推翻了。后来想到了递归这种解法,每一次判断他九种走法的最合适的值,就是实现起来很难,思路还是卡住了。
最后想不出来看了别人的答案,那就看看别人的思路吧
这里他先定义了一系列静态变量
static Scanner sr = new Scanner(System.in);
static int n = sr.nextInt();
static int m = sr.nextInt();
static int[][] map = new int[n][m];
static int dx[] = {0,0,0,1,2,3,1,2,1};
static int dy[] = {1,2,3,0,0,0,1,1,2};
static int max_length = Integer.MIN_VALUE;
其中这两个数组
static int dx[] = {0,0,0,1,2,3,1,2,1};
static int dy[] = {1,2,3,0,0,0,1,1,2};
//这种方法非常简便,比我想得简单多了
对应他要走的九种可能
static int max_length = Integer.MIN_VALUE;
//规定了一个最小的int类型的数,方便在以后取较大值
//因为最后的结果可能是负数,所以没有初始位零
//细啊 太细了
输入数据,调用函数,输出,没什么好说的
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
map[i][j] = sr.nextInt();
}
}
dfs(0,0, map[0][0]);
System.out.println(max_length);
主要看递归
private static void dfs(int i, int j, int length) {
// TODO Auto-generated method stub
if(i==n-1 && j== m-1)
max_length = Math.max(length, max_length);//更新最长长度
for (int k = 0; k < dx.length; k++) {
int nx = i + dx[k];
int ny = j + dy[k];
//根据范围内坐标进行递归
if (nx >= 0 && ny >= 0 && nx < n && ny < m ) {
dfs(nx,ny,length+map[nx][ny]);//进行递归
}
}
}
先用一个for循环来计算九种走法,每一种走法又调用了一次函数
这里他限制范围用了
nx >= 0 && ny >= 0 && nx < n && ny < m
当上面循环出的结果不在这个范围内就不会进入递归,避免越界,很妙
至于最后为什么没有return,函数出口在哪里,我也是想了很久
整体递归思路 这是3x4的一个图 要走到2.3的点
0.0 | |||
2.3 |
第一次for循环,(0.1)往下走
0.0 | |||
0.1 | |||
2.3 |
符合条件,进入递归,再循环,再往下
0.0 | |||
0.1 | |||
0.2 | 2.3 |
这时再for循环,前三次都是向下走,不会进入递归,第四次往右走,符合条件
0.0 | |||
0.1 | |||
0.2 | 1.2 | 2.3 |
以此类推,直到走到目的地
0.0 | |||
0.1 | |||
0.2 | 1.2 | 2.2 | 2.3 |
符合判断条件后最后一次进入递归
因为是第一次完成整个路程,最大的长度就是本次长度
if(i==n-1 && j== m-1)
max_length = Math.max(length, max_length);//更新最长长度
这时for循环完也不会进入递归,这次的路线就结束了
之后的路线结束后会跟之前的长度比较,取较大的值
这时候就体现了静态变量的用处,也就是在全局有效,不用返回值了
3.提交结果
4.
这次的题对我来说很难,在思考的过程中有了大概的方向,了解了别人的代码也知道了自己跟大佬的差距,要仔细体会别人的做题方式,多学习
5.正确代码
import java.util.Scanner;
public class Main {
static Scanner sr = new Scanner(System.in);
static int n = sr.nextInt();
static int m = sr.nextInt();
static int[][] map = new int[n][m];
static int dx[] = {0,0,0,1,2,3,1,2,1};
static int dy[] = {1,2,3,0,0,0,1,1,2};
static int max_length = Integer.MIN_VALUE;
public static void main(String[] args) {
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
map[i][j] = sr.nextInt();
}
}
dfs(0,0, map[0][0]);
System.out.println(max_length);
}
private static void dfs(int i, int j, int length) {
// TODO Auto-generated method stub
if(i==n-1 && j== m-1)
max_length = Math.max(length, max_length);//更新最长长度
for (int k = 0; k < dx.length; k++) {
int nx = i + dx[k];
int ny = j + dy[k];
//根据范围内坐标进行递归
if (nx >= 0 && ny >= 0 && nx < n && ny < m ) {
dfs(nx,ny,length+map[nx][ny]);//进行递归
}
}
}
}
6.错误代码
因为思路没想明白,敲了很多零碎的代码,也没保存