all possible paths for the robot
本问题已经有最佳答案,请猛点这里访问。
想象一下,一个机器人坐在NxN网格的左上角。机器人只能在两个方向上移动:向右和向下。想象一下,某些正方形是"限制范围",以至于机器人无法踩到它们。设计算法以获取机器人的所有可能路径。
这是我得到的参考实现,我认为该实现是错误的,因为它只找到一条路径,而不是所有可能的路径(更多详细信息,在第10行中,只有在没有正确的路径的情况下,机器人才会下降。)为了找到所有可能的路径,机器人应该同时尝试正确和向下的操作)?要确认我的理解是正确的。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | ArrayList<Point> current_path = new ArrayList<Point>(); public static boolean getPaths(int x, int y) { Point p = new Point(x, y); current_path.add(p); if (0 == x && 0 == y) return true; // current_path boolean success = false; if (x >= 1 && is_free(x - 1, y)) { // Try right success = getPaths(x - 1, y); // Free! Go right } if (!success && y >= 1 && is_free(x, y - 1)) { // Try down success = getPaths(x, y - 1); // Free! Go down } if (!success) { current_path.remove(p); // Wrong way! } return success; } |
先谢谢了,
林
这是您可以做的:
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 37 38 39 40 41 42 43 44 45 46 | public static class Point { int x, y; public Point (int x, int y) { this.x = x; this.y = y; } @Override public String toString() { return String.format("[%d, %d]", x, y); } } public static void getPathsRec(int x, int y, Deque<Point> currentPath, List<List<Point>> paths) { if (x == 0 && y == 0) { List<Point> path = new ArrayList<Point>(); for (Point p : currentPath) path.add(p); paths.add(path); //System.out.println(currentPath); return; } if (x > 0 && is_free(x-1, y)) { currentPath.push(new Point(x-1, y)); getPathsRec(x-1, y, currentPath, paths); currentPath.pop(); } if (y > 0 && is_free(x, y-1)) { currentPath.push(new Point(x, y-1)); getPathsRec(x, y-1, currentPath, paths); currentPath.pop(); } } static int n = 2; public static List<List<Point>> getPaths() { List<List<Point>> paths = new ArrayList<List<Point>>(); Deque<Point> d = new ArrayDeque<Point>(); d.push(new Point(n-1, n-1)); getPathsRec(n - 1, n - 1, d, paths); //System.out.println(paths); return paths; } |
这是一个简单的回溯。这个想法是递归地访问下一个状态,但是要确保在调用之后状态返回到其先前的状态(就像在调用之前一样)。这是通过从
请注意,为简单起见,您可以引入新的类
1 2 3 | class Path { List<Point> points; } |
使代码更具可读性。然后
还可以考虑重新定义
您的解决方案是错误的,因为一旦达到
下面是您的问题的示例答案。它使用回溯算法:
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 37 | public class test { static int n = 3; //substitute your n value here static ArrayList<Point> current_path = new ArrayList<Point>(); static boolean[][] blockedCell = new boolean[n][n]; public static void FindAllWay(int x, int y) { if (x <0 || y < 0) return; Point p = new Point(x, y); current_path.add(p); if (0 == x && 0 == y){ System.out.println(current_path.toString()); current_path.remove(current_path.size()-1); return; } if ((x > 0) && !blockedCell[x-1][y]) //go right { blockedCell[x-1][y] = true; FindAllWay(x-1, y); blockedCell[x-1][y] = false; } if ((y > 0) &&!blockedCell[x][y-1]) // go down { blockedCell[x][y-1] = true; FindAllWay(x, y-1); blockedCell[x][y-1] = false; } current_path.remove(current_path.size()-1); } public static void main(String[] args) { FindAllWay(n-1,n-1); } } |