【问题标题】:Method doesn't go through 2d array方法不通过二维数组
【发布时间】:2021-02-07 14:31:54
【问题描述】:

我正在做一个像迷宫一样通过二维数组的方法,目标是到达包含整数 0 的位置。我能够记录路径,但它不会移动,它保持在初始位置。
这是我所说的不动的例子:
Please input the size of the board (between 5 and 20):
5
Please choose a starting index from the 4 options below:
    Press 1 for "top-left"
    Press 2 for "top-right"
    Press 3 for "bottom-left"
    Press 4 for "bottom-rigth"
Enter your choice:
1
2   1   1   1   4   
2   3   4   1   3   
1   1   1   2   4   
3   0   3   3   2   
3   2   3   4   2   
Move south 2, Move north 2, Move east 2, Move west 2, 

有人可以帮帮我吗?
到目前为止,这是我的方法:

public static boolean MagicBoard_recursive(int[][] board, int size, int startRow, int startCol) {
        boolean solvable = true;
        int number = board[startRow][startCol];

        int[] moves = {startRow+number, startRow-number, startCol+number, startCol-number}; // This array contains all the possible moves we can do
        
        
        for(int i = 0; i < 4; i++) {
            // If we reached the position containing the integer 0
            if(board[startRow][startCol] == 0) {
                solvable = true;
                break;
            }
            if(startRow+number > size && startRow-number < 0 && startCol+number > size && startCol-number<0) {
                solvable = false;
                break;
            }
            solvable = true;
            // If we try moving south
            if(i == 0) {
                //int destinationNumber = board[startRow+number][startCol];
                // If we move to this position, will we be able to continue, if not, then we try another move
                if(startRow+number > size) {
                    solvable = false;
                    continue;
                }
                else {
                    while(solvable) {
                        startRow +=number;
                        System.out.print("Move south " + number + ", ");
                        MagicBoard_recursive(board, size, startRow, startCol);
                    }
                }
            }
            
            // If try moving north
            else if(i == 1) {
                // If we move to this position, will we be able to continue. If not, then we try another move
                if(startRow-number < 0) {
                    solvable = false;
                    continue;
                }
                else {
                    while(solvable) {
                        startRow -=number;
                        System.out.print("Move south " + number + ", ");
                        MagicBoard_recursive(board, size, startRow, startCol);
                    }
                }
            }
            
            // If try moving east
            else if(i == 2) {
                if(startCol+number > size) {
                    solvable = false;
                    continue;
                }
                else {
                    while(solvable) {
                        startCol += number;
                        System.out.print("Move east " + number + ", ");
                        MagicBoard_recursive(board, size, startRow, startCol);
                    }
                }
            }
            
            // If try moving west
            else if(i == 3) {
                if(startCol-number < 0) {
                    solvable = false;
                    break;
                }
                else {
                    while(solvable) {
                        startCol -=number;
                        System.out.print("Move west " + number + ", ");
                        MagicBoard_recursive(board, size, startRow, startCol);
                    }
                }
            }
        }
        return solvable;
    }

这是一张图片,展示了程序解决棋盘的动作示例:

【问题讨论】:

  • 我觉得你需要进一步澄清运动是如何发生的。我仍然不太了解所需的运动机制。
  • @OmarAbdelBari,我会尝试更好地解释自己。我要做的是一个包含小于或等于板尺寸的随机数的板,并且有一个位置包含整数 0。根据用户选择的起始位置,可能有也可能没有包含整数 0 的位置的可能路径。如果可以解决它,我必须记录程序采用的路径。如果没有可能到达 0 的路径,那么我必须返回 false。我的解释清楚了吗?
  • 什么是合法的举动?例如,在#1 中,我向南移动。为什么它在#2 中一直到板底?
  • @NomadMaker 圆圈标记板上的开始位置。圆圈中的整数表示圆圈可以在棋盘上移动一定数量的方块。在一个步骤中,圆圈可以向东、向西、向北或向南移动。在每一步,选择的方向都是固定的。圆圈不能移出棋盘。唯一合法的起始位置是四个角方块。棋盘必须恰好包含一个目标方格,其值为 0,可以位于棋盘上的任何位置。
  • @Jennifer 我认为有一种更简单的方法可以使用队列和类似于广度优先搜索的方法来解决这个问题。

标签: java recursion multidimensional-array


【解决方案1】:

我认为你所采取的方法比它需要的更困难。

考虑使用 Tile[][] 之类的东西代替代表棋盘的 int[][] 数组,其中 Tile 是包含以下属性的类。 p>

public class Tile {
    boolean visited;
    int value; //Maybe short will suffice instead?
}

visited 属性的重点是确保您不会重复测试您之前已经访问过的可到达图块,例如在广度优先或深度优先搜索中。

那么你可能有一个使用队列的类。对我和 Java 来说已经有一段时间了,但是对于这种情况,候选人似乎像 ArrayDeque(由于它的可调整性)。在包含您的方法的类中,您可以将其添加为成员。

ArrayDeque<TileCoordinate> tilesToVisit = new ArrayDeque<>();

TileCoordinate 对象只是一个包含对象坐标的类。如果您愿意,您可以将坐标直接放入 Tile,但我更喜欢将它们分开。

public class TileCoordinate
{
    public int x;
    public int y;

    public TileCoordinate(int x, int y) {
        this.x = x;
        this.y = y;
    }
}

那么,这将如何帮助您简化问题。当用户第一次选择起始角时,您将坐标插入队列而不是直接处理它。之后,您可以创建一个循环访问队列中的任何坐标。

//Get input regarding starting corner from user then,
tilesToVisit.add(new TileCoordinate(x, y)); //Insert coordinate corner into queue

while (!tilesToVisit.isEmpty && solvable == false) {
    TileCoordinate tileToVisit = tilesToVisit.removeFirst();
        
    Visit(tileToVisit); //This is where your business logic happens
}

//If loop is completed before solvable is set to true, this means it's not solvable

然后在您的流程方法中,您可能希望应用您的移动逻辑来确定您的队列中还有哪些要访问的内容。

public static void Visit(TileCoordinate coord) {
    Tile tile = board[coord.x, coord.y];
    tile.visited = true; //Make sure you do this first so you don't process this again later!
    
    if (tile.value == 0) {
        //mark solvable to true, which would be a class state variable
    }
    
    //Foreach tile that is reachable from this tile where visited = false, add into your queue 'unvisitedReachableTileCoordinate'
    tilesToVisit.Add(unvisitedReachableTileCoordinate);
}

抱歉,我有一段时间没有编写 Java 代码了,而且我的 netbeans 设置搞砸了。但是,我确实在 oracle 文档中查找了许多这些函数,因此它通常应该可以工作。这应该可以让您大致了解这种方法。

【讨论】:

    猜你喜欢
    • 2018-12-28
    • 2018-06-25
    • 2018-04-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-12-08
    • 2010-12-19
    • 1970-01-01
    相关资源
    最近更新 更多