【问题标题】:A* Search ImplementationA* 搜索实现
【发布时间】:2014-02-17 22:04:29
【问题描述】:

我正在尝试在 Java 中实现 A* 搜索算法来查找给定迷宫的路径。迷宫有一个开始和目标状态,并且可能包含障碍物。

这是我解决给定迷宫的代码:

  public Solver(Maze maze) 
  {

  explored = new HashSet<Square>(); // Set of squares that A* has investigated
  path = new ArrayList<Square>(); // List of squares to the goal
  Square currentSquare = maze.getStart();
  Square goalSquare = maze.getGoal();

  while (currentSquare.equals(goalSquare) != true)
  {
      System.out.println("Im here");


      // Calculate each direction from the current node
      Square left = new Square(currentSquare.getRow(), currentSquare.getColumn()         - 1);
      Square right = new Square(currentSquare.getRow(), currentSquare.getColumn() + 1);
      Square top = new Square(currentSquare.getRow() - 1, currentSquare.getColumn());
      Square bottom = new Square(currentSquare.getRow() + 1, currentSquare.getColumn());

      // Check if each direction is blocked. If it is, we cant go there.
      List<Square> possibilities = new ArrayList<Square>();

      if (maze.isBlocked(left) != true && path.contains(left) != true)
      {
          possibilities.add(left);
      }
      if (maze.isBlocked(right) != true && path.contains(right) != true)
      {
          possibilities.add(right);
      }
      if (maze.isBlocked(top) != true && path.contains(top) != true)
      {
          possibilities.add(top);
      }
      if (maze.isBlocked(bottom) != true && path.contains(bottom) != true)
      {
          possibilities.add(bottom);
      }

      // find which square we should go to next
      Square choice = currentSquare;
      int choicegx =  1000;//path.size();
      int choicehx = 1000;//Math.abs(goalSquare.getRow() - choice.getRow()) + Math.abs(goalSquare.getColumn() - choice.getColumn());
      int choicefx = 1000;//choicegx + choicehx;
      for (Square possibility : possibilities)
      {
          int fx = 0;
          int gx = 0;
          int hx = 0;

          // Calculate gx (distance traveled)
          gx = path.size();

          // Calculate hx (Manhatten distance)
          hx = Math.abs(goalSquare.getRow() - possibility.getRow()) + Math.abs(goalSquare.getColumn() - possibility.getColumn());

          // Calculate fx
          fx = gx + hx;

          if (fx < choicefx)
          { // Possibility is a better choice based on fx
              choicefx = fx;
              choicehx = hx;
              choicegx = gx;
              choice = possibility;
              if (choice.equals(goalSquare) != true && choice.equals(maze.getStart()) != true)
              {
                  explored.add(choice);
              }
          }
          else if (fx == choicefx)
          { // Squares are tied based on fx
              if (hx < choicehx)
              { // Possibility is better based on hx
                  choicefx = fx;
                  choicehx = hx;
                  choicegx = gx;
                  choice = possibility;
                  if (choice.equals(goalSquare) != true && choice.equals(maze.getStart()) != true)
                  {
                      explored.add(choice);
                  }
              }
              else if (hx == choicehx)
              { // Squares are tied based on hx
                  if (possibility.getRow() < choice.getRow())
                  {// Possibility is better based on row
                      choicefx = fx;
                      choicehx = hx;
                      choicegx = gx;
                      choice = possibility;
                      if (choice.equals(goalSquare) != true && choice.equals(maze.getStart()) != true)
                      {
                          explored.add(choice);
                      }
                  }
                  else if (possibility.getRow() == choice.getRow())
                  { // Squares are tied based on row
                      if (possibility.getColumn() < choice.getColumn())
                      { // Squares are tied based on column
                          choicefx = fx;
                          choicehx = hx;
                          choicegx = gx;
                          choice = possibility;
                          if (choice.equals(goalSquare) != true && choice.equals(maze.getStart()) != true)
                          {
                              explored.add(choice);
                          }
                      }
                  }
              }
          }
      }

      // Move to the square we have chosen and add to path
      currentSquare = choice;
      if (currentSquare.equals(goalSquare) != true)
      {
          path.add(currentSquare);
      }

  }
}

我正在尝试确定设计此部分的更好方法:

Square choice = currentSquare;
      int choicegx =  1000;//path.size();
      int choicehx = 1000;//Math.abs(goalSquare.getRow() - choice.getRow()) +     Math.abs(goalSquare.getColumn() - choice.getColumn());
      int choicefx = 1000;//choicegx + choicehx;

在本节中,我会先确定初始效果,然后再查看我选择的方格。最初,我一直在使用当前节点的 fx 来设置这些值。但是,然后我遇到了一个问题,即从不探索比当前节点更差的节点。我希望一直在进步,从不停留在不是目标的节点上。

有什么建议吗?

【问题讨论】:

    标签: java search a-star


    【解决方案1】:

    尝试查看Priority queue。它是一种用于“调度”您尚未访问的节点访问的结构。当你访问一个节点时,可以从当前节点计算出所有可以访问的节点的gx,然后将这些节点存储在优先级队列中,按照gx的值排序,使得@987654324最低的节点@在上面。

    然后从队列的顶部挑选下一个要访问的节点,因此它可以是当前节点之一,但也可以是较旧的节点,如果它的gx 低于任何其他剩余节点。这样您就可以随时探索当前最有趣的路径。

    【讨论】:

      猜你喜欢
      • 2016-12-20
      • 1970-01-01
      • 1970-01-01
      • 2016-04-22
      • 2011-09-09
      • 1970-01-01
      • 1970-01-01
      • 2019-07-01
      • 2014-05-21
      相关资源
      最近更新 更多