我正在努力完成一个高中编程项目,但是一个错误阻止我完成。该计划/项目旨在解决“非攻击女王”问题。拼图,即在棋盘上找到女王的所有位置,其中同一行,列或对角线中没有两个女王。我们被要求使用递归来解决这个问题。
现在,我遇到的问题是双重问题。首先,每次我在特定索引处向solvedChessBoards
数组添加解决方案时,尽管我在赋值中只使用了一个索引,但是数组的所有元素都会更新到这个最新的解决方案。这意味着一旦我解决了所有可能的解决方案,我的数组只包含一个解决方案(最后一个解决方案),但只是几次。
第二个问题是,一旦solveBoard()
方法完成执行,solvedChessBoards
数组将丢失其所有值,尽管它是一个类变量。当我尝试打印所有解决方案时,这是有问题的,因为阵列不再包含任何信息。
我认为这个问题源于对递归的误解以及数据如何存储在java中。我希望有人不仅可以帮助我解决问题,而且还可以教导'我,我做错了什么,以便我将来可以避免类似的问题。
请注意,虽然Board
类中的其他方法很重要,但我不认为该bug源自solveBoard
方法以外的任何方法。出于这个原因,我认为唯一虔诚的代码就在这个方法中。
以下是我的Board
课程的代码:
/**
* Class that creates a board of given equal dimensions. Also has methods and variables pertaining to
* Queen chesspieces that can be placed on the board.
*
* @Andrew Smith
* @2/14/16
*/
public class Board
{
private int solvedBoardCount;
private final int QUEEN = 1, EMPTY = 0;
private int expectedSolutions;
private int[][] chessBoard;
private int[][][] solvedChessBoards;
//---------------------------------------------------------------------------------------------------------------------------------------------
// Creates a chess Board object with given dimensions. Each Board is square, with equal sides.
//---------------------------------------------------------------------------------------------------------------------------------------------
public Board (int dimension, int solutions) {
chessBoard = new int[dimension][dimension];
expectedSolutions = solutions;
solvedChessBoards = new int[expectedSolutions][dimension][dimension];
solveBoard(0, chessBoard);
}
//---------------------------------------------------------------------------------------------------------------------------------------------
// Creates the default chess Board object with dimensions of 4 on each side.
//---------------------------------------------------------------------------------------------------------------------------------------------
public Board () {
chessBoard = new int[4][4];
solvedChessBoards = new int[1][4][4];
solveBoard(0, chessBoard);
}
//---------------------------------------------------------------------------------------------------------------------------------------------
// This method does two things.
// First, it solves the given chess board under the rules of the "Non-Attacking Queens" puzzle. It does this recursively, iterating through
// all possible combinations of queen placement.
//
// Secondly, the method solves for every possible solution to the puzzle, and cataloges these solution 'boards' in the variable
// solvedChessBoards, a three dimensional array of 2 dimensional boards.
//---------------------------------------------------------------------------------------------------------------------------------------------
private void solveBoard(int row, int[][] tempBoard) {
for (int column = 0; column < tempBoard.length; column++) { //Goes across the columns of a given row
if (indexIsSafe(row, column)) { //Checks to see if the queen placement is valid
tempBoard[row][column] = QUEEN; //Sets placevalue of 1
if (row < tempBoard.length - 1) { //Unless the board has been solved
solveBoard(row+1, tempBoard);
deleteLastPosition(row);
}else{
solvedChessBoards[solvedBoardCount] = tempBoard; //Adds solved chessboard to the array
solvedBoardCount++;
deleteLastPosition(row);
}
}
}
}
//---------------------------------------------------------------------------------------------------------------------------------------------
// Takes a current row and column and tests to see if it is a viable spot for a queen.
// This would mean no queens above or in a diagonal path.
//---------------------------------------------------------------------------------------------------------------------------------------------
private boolean indexIsSafe(int currentRow, int currentColumn) { //Tests the current index; Returns True if a queen can be placed
int diagonal = 1; //Used to add/subtract in order to line up the diagonals of the chess board
for (int testRow = currentRow - 1; testRow >= 0; testRow--) {
if (chessBoard[testRow][currentColumn] == 1) { //Queen directly ABOVE
return false;
}
//First checks to make sure there is an index to the left
if (currentColumn - diagonal >= 0 && chessBoard[testRow][currentColumn - diagonal] == 1) { //Queen on LEFT DIAGONAL
return false;
}
//First checks to make sure there is an index to the right
if (currentColumn + diagonal < chessBoard.length && chessBoard[testRow][currentColumn + diagonal] == 1) { //Queen on RIGHT DIAGONAL
return false;
}
diagonal += 1; //Adjusts for the increasing distance of diagonals
}
return true; //A queen can be placed at the current index
}
//---------------------------------------------------------------------------------------------------------------------------------------------
// Deletes the last position (1 row above) in the given board. This is used to allow the program to progress along the columns without
// containing past queen placements.
//---------------------------------------------------------------------------------------------------------------------------------------------
private void deleteLastPosition (int currentRow) {
for (int column = 0; column < chessBoard.length; column++) { //Finds the queen in the row above the current row
if (chessBoard[currentRow][column] == 1) {
chessBoard[currentRow][column] = EMPTY;
}
}
}
//---------------------------------------------------------------------------------------------------------------------------------------------
// Prints the chess Board by returning a formatted string.
// Empty spaces are represented by 0s, and queens by 1's.
//---------------------------------------------------------------------------------------------------------------------------------------------
public String toString () {
String result = "";
for (int[][] solvedBoard: solvedChessBoards) {
for (int row = 0; row < solvedBoard.length; row++) {
for (int column = 0; column < solvedBoard.length; column++) {
result += solvedBoard[row][column];
}
result += "\n";
}
result += "\n--------------------------------------------- \n";
}
return result;
}
}
...和我的司机班:
/**
* Solves the Non-Attacking Queens Problem. In order to solve this riddle, a set of Queens must be placed
* on a blank chess board in a way that no queen is in the same column, row, or diagonal.
*
* @Andrew Smith
* @1/3/16
*/
public class QueensDriver
{
public static void main (String[] args) {
Board chessBoard = new Board(8,92);
System.out.print (chessBoard);
}
}
对于那些愿意提供帮助的人,请提前非常感谢。