簡體   English   中英

使用遞歸通過Java中的國際象棋騎士移動模式在2D數組中放置數字

[英]Placing numbers in a 2D array by a chess knight move pattern in Java using recursion

public class ChessComplete 
{
    private int size;
    private int[][] board;
    private long callNum;

    public ChessComplete(int size)//constructor with 2D array size as a parameter
    {
        this.size = size;
        board = new int [size][size];
        board[0][0] = 1;
    }
    public boolean isValid(int r, int c)//To check the if the number that is added is in the 2D array is in bound
    {
        if(r < 0 || c < 0 || r >= size || c >= size)
        {
            return false;
        }
        return true;
    }

    /*
     * Move through the 2D array by placing the consecutive number for each (row,col) until its full
     * Moves Are only allowed in a chess knight pattern
     */
    public boolean move(int r, int c, int count) {
    callNum++;

    if (!isValid(r, c)) {
        return false;
    }

    if (count == (size * size))// Base case if count reaches the end of 2D
                                // array

    {

        return true;
    }
    board[r][c] = count;// fills the positon with the current count

    if (board[r][c] == 0) {
        return false;
    }

    // Check if each possible move is valid or not
    if (board[r][c] != 0) {

        for (int i = 0; i < 8; i++) {

            int X[] = { 2, 1, -1, -2, -2, -1, 1, 2 };
            int Y[] = { 1, 2, 2, 1, -1, -2, -2, -1 };

            // Position of knight after move
            int x = r + X[i];
            int y = c + Y[i];

            if (move(x, y, count + 1)) {

                return move(x, y, count + 1);
            }

        }
    }
    board[r][c] = 0;
    return false;
}
    public long getSteps()//Number of reccursive trials
    {
        return callNum;
    }
    public void displayBoard()
    {
        String s = " ";
        for(int r = 0; r < size; r++)
        {
            for(int c = 0; c < size; c++)
            {
                System.out.print(board[r][c] + " ");
            }
            System.out.println();
        }

    }
}

輸出為:

1,  0,  0,  0,  0, 

0,  0,  0,  23, 0, 

0,  2,  0,  0,  0, 

0,  0,  0,  0, 24, 

0,  0,  3,  0,  0 

Recursive method call count: 78,293,671

說明

注意,在位置(行,列) (0, 0)有一個1 ,在位置(2, 1)2 如您所見,棋盤中的騎士以類似的方式移動。 這樣,我們需要用連續的數字填充整個2D數組,以使其嚴格遵循騎士模式。

問題

我不明白為什么整個2D數組沒有被所有其他連續數字填充。 例如,在2D數組中用3填充位置后,數字會一直跳到23。

在執行移動之前,您無需檢查正方形是否已被占用,因此您的解決方案包括重復寫入的重復移動。

更改isValid以檢查目標正方形是否為空:

public boolean isValid(int r, int c) {
    if (r < 0 || c < 0 || r >= size || c >= size || board[r][c] != 0) {
        return false;
    }
    return true;
}

...並刪除初始化步驟board[0][0] = 1; 在構造函數中(應該通過對move的第一個調用來設置)。

另外(但不是致命的),

if (move(x, y, count + 1)) {
    return move(x, y, count + 1);
}

應該

if (move(x, y, count + 1)) {
    return true;
}

並且檢查if (board[r][c] == 0)if (board[r][c] != 0)是否不執行任何操作,因為它們是在設置board[r][c] = count;

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM