当前位置: 首页 > 知识库问答 >
问题:

递归骑士之旅中变量的正确声明(Java家庭作业)

盛跃
2023-03-14
   else{
   for(int i = 0; i < numberOfPossibleNextMoves; i++){
      Cell nextCellToMoveTo = candidateNextMoves.get(i);

      int currentRowStorage = currentRow;
      int currentColumnStorage = currentColumn;
      currentRow = nextCellToMoveTo.row;
      currentColumn = nextCellToMoveTo.column;

      listOfMoves.add(nextCellToMoveTo);
      chessBoard[currentRow][currentColumn] = 1;
      currentMoveNumber++;

      boolean tourFound = findTour();

      if(tourFound){
         return true;
            }
            else{ // Undo the last move just made
               backtrackCount++;
               chessBoard[currentRow][currentColumn] = -1;
               currentRow = currentRowStorage;
               currentColumn = currentColumnStorage;                           
               listOfMoves.remove(nextCellToMoveTo);
               currentMoveNumber--;         
            }
         }
         return false;
chessBoard[currentRow][currentColumn] = -1;
currentRow = currentRowStorage;
currentColumn = currentColumnStorage;

这部分代码将棋盘中的平方更改为-1,这意味着它是未访问的(1=visited)。正如上面所示,新移动的currentRow和currentColumn用于将正方形设置为unvated。然后使用currentRowStorage和CurrentColumnStorage将这些值重置为以前的跳转值。

如果我将代码更改为

currentRow = currentRowStorage;
currentColumn = currentColumnStorage;
chessBoard[currentRow][currentColumn] = -1;

它成功地发现了一个错误的巡回赛,其中最后1/3左右的动作只是在几个方块之间来回跳跃。这是意料之中的,因为它不能正确地处理重置过程。

如果游览未完成,那么findTour将确定从骑士的当前单元格可以访问的空单元格列表(可能是空的),并将该列表存储在本地声明的列表变量CandidateNextMoves中。此列表变量必须声明为方法的本地变量。如果此列表为空,则无法扩展当前的部分游览,因此findTour应返回false。如果列表不是空的,那么findTour尝试通过列表上的每一步来扩展游览,如下所示。它在列表上迭代,对于列表的每个单元格,它向该单元格进行下一次移动,更新所有L(巡回赛中的移动列表)、B(板状态的2D数组(已访问,未访问))、currRow和currCol以反映此移动。然后它递归地调用自己,将调用的结果赋给一个本地声明的布尔变量,您可以将其命名为“success”。如果success被指定为true,则findTour返回true。如果成功为假,findTour将撤消它刚刚进行的移动,或者“回溯”,并尝试CandidateNextMoves的下一个移动。您将维护一个静态int变量backtrackCount,该变量初始化为0,并在每次撤消移动时递增。

一个提示--我把我的布尔语言称为“发现之旅”,而不是“成功”。

共有1个答案

年文柏
2023-03-14

就像无限递归的情况一样,首先要检查的是你计划如何摆脱它的条件。在这种情况下,只有在

if(currentMoveNumber == numberOfMovesOnBoard){
     return true;
  }

检查算法和初始化是否会阻止currentMoveNumber达到NumberOfMoveSonboard。

提示:在您进入递归方法之前,您的起始条件是什么?

 类似资料:
  • 我认为在这篇文章中粘贴整个类可能代码太多(可能不够相关),所以我在这里显示它们: graph.java depthFirstSearch.java 可能的骑士步骤是这样定义的(在主类中)(使用图的边G): 以下是我试图找到的可能的旅行: 例如,如果我试图通过调用这个递归函数,它应该使用字段上的每个平方返回该平方中所有可能的tour()。 未标记的方块是已经到达的方块,在同一次旅行中不应该再访问了。

  • 我正在尝试编写骑士之旅递归算法: 谁能告诉我哪里出错了?我已经一步一步地检查了什么池算法正在添加到列表中。什么是大惊奇算法在添加4,3池和6,4池后,应该用6,4作为实际位置来称呼它自己,但我不知道为什么它用4,3作为实际位置来称呼自己。

  • 另一个经典问题,我们可以用来说明第二个通用图算法称为 “骑士之旅”。骑士之旅图是在一个棋盘上用一个棋子当骑士玩。图的目的是找到一系列的动作,让骑士访问板上的每格一次。一个这样的序列被称为“旅游”。骑士的旅游难题已经吸引了象棋玩家,数学家和计算机科学家多年。一个 $$8 \times 8$$ 棋盘的可能的游览次数的上限为 $$1.305 \times 10^{35}$$ ;然而,还有更多可能的死胡同

  • 有最后关于骑士之旅一个有趣的话题,然后我们将继续到深度优先搜索的通用版本。主题是性能。特别是,knightTour 对于你选择下一个要访问的顶点的方法非常敏感。例如,在一个5乘5的板上,你可以在快速计算机上处理路径花费大约1.5秒。但是如果你尝试一个 $$8 \times 8$$ 的板,会发生什么?在这种情况下,根据计算机的速度,你可能需要等待半小时才能获得结果!这样做的原因是我们到目前为止所实现

  • 我们将用来解决骑士旅游问题的搜索算法称为 深度优先搜索(DFS)。尽管在前面部分中讨论的广度优先搜索算法一次建立一个搜索树,但是深度优先搜索通过尽可能深地探索树的一个分支来创建搜索树。在本节中,我们将介绍实现深度优先搜索的两种算法。我们将看到的第一个算法通过明确地禁止一个节点被访问多次来直接解决骑士的旅行问题。第二种实现是更通用的,但是允许在构建树时多次访问节点。第二个版本在后续部分中用于开发其他

  • 为了将骑士的旅游问题表示为图,我们将使用以下两个点:棋盘上的每个正方形可以表示为图形中的一个节点。 骑士的每个合法移动可以表示为图形中的边。 Figure 1 展示了骑士的移动以及图中的对应边。 Figure 1 要构建一个 n*n 的完整图,我们可以使用 Listing 1 中所示的 Python 函数。knightGraph 函数在整个板上进行一次遍历。 在板上的每个方块上,knightGra