Java 有趣的system.exit()行为和中断行为-发生了什么?

Java 有趣的system.exit()行为和中断行为-发生了什么?,java,break,Java,Break,我正在尝试按如下方式实施BFS: package search; import java.io.BufferedWriter; import java.io.File; import java.io.FileWriter; import java.io.IOException; import java.util.ArrayList; import java.util.Collections; import java.util.LinkedList; import java.util.Qu

我正在尝试按如下方式实施BFS:

package search;

   import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.LinkedList;
import java.util.Queue;

import common.MyNode;
import common.Parser;

public class BFS extends Search {

    Queue<MyNode> frontier;
    Queue<MyNode> visited;
    ArrayList<MyNode> route;
    Parser p;
    boolean found = false;
    private int toWriteInt = 0;
    private double distance;

public BFS(MyNode startNode, MyNode goalNode, Parser p) {
    super(startNode, goalNode, p);
    frontier = new LinkedList<MyNode>();
    visited = new LinkedList<MyNode>();
    this.p = p;
    route = new ArrayList<MyNode>();

}

public void Search() {

    visited.add(this.getStartNode());

    if (isGoal(this.getStartNode())) {
        System.out.println("goal found at start");
        goalFound();
    }
    ArrayList<MyNode> successors = this.getStartNode().getSuccessors();

    for (int i = 0; i < successors.size(); i++) {
        successors.get(i).setParent(this.getStartNode());
        if (!(visited.contains(successors.get(i)))
                && !(frontier.contains(successors.get(i)))) {
            if (isGoal(successors.get(i))) {
                visited.add(successors.get(i));
                System.out.println("goal found at start successor");

                goalFound();
                break;
            } else {
                frontier.add(successors.get(i));

            }

        }

    }
    while (!frontier.isEmpty()) {
        MyNode current = frontier.poll();

        ArrayList<MyNode> currentSuccessors = current.getSuccessors();

        visited.add(current);

        for (int i = 0; i < currentSuccessors.size(); i++) {

            if (!(visited.contains(currentSuccessors.get(i)))
                    && !(frontier.contains(currentSuccessors.get(i)))) {
                currentSuccessors.get(i).setParent(current);

                if (isGoal(currentSuccessors.get(i))) {
                    visited.add(currentSuccessors.get(i));
                    System.out.println("goal found in loop");
                    goalFound();
                    break;
                } else {
                    frontier.add(currentSuccessors.get(i));
                }

            }

        }
    }
}

private boolean isGoal(MyNode toCheck) {
    boolean goal = false;
    if (toCheck.equals(this.getGoalNode())) {
        goal = true;
    }
    return goal;

}

private void goalFound() {
    System.out.println("goal found with " + visited.size());
    printRoute();
    System.exit(0);

}
public void printRoute() {
        MyNode i = this.getGoalNode();
        while (i.getParent() != null) {

            System.out.println(i.getId());
            distance = distance
                    + Search.distFrom(i.getLat(), i.getLon(), i.getParent()
                            .getLat(), i.getParent().getLon());

            i = i.getParent();

        }
        System.out.println(this.startNode.getId());


        System.out.println("completed routing");
        System.out.println("path length of " + distance + "km");
    }
}

再一次,这可以很好地工作并打印出正确的路线。但是,如果我删除system.exit(0),代码将不起作用,printRoute()的while循环将永远打印,将相同的两个节点打印两次(i和i.getParent()。我觉得这真的很奇怪,因为该方法必须已经完成,才能命中我的system.exit

谁能告诉我这是为什么?必须调用system.exit是非常有问题的,因为我想在代码中嵌入BFS,这意味着我不能

谢谢, MJB

编辑:下面有人建议退货可以解决我的问题。以下是一个*搜索,显示相同的行为,仅在我返回系统时有效。即使返回,也要退出:

    package search;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Stack;

import common.MyNode;
import common.Parser;

public class AStar extends Search {

    private ArrayList<MyNode> openList; // This is basically our frontier
    private ArrayList<MyNode> closedList;// This is the visited set.

    public AStar(MyNode startNode, MyNode goalNode, Parser p) {
        super(startNode, goalNode, p);
        openList = new ArrayList<MyNode>();
        closedList = new ArrayList<MyNode>();

    }

    public Stack<MyNode> Search() {
        Stack<MyNode> toReturn = new Stack<MyNode>();
        openList.add(this.getStartNode());
        while (!openList.isEmpty()) {

            Collections.sort(openList);
            MyNode q = openList.remove(0);
            openList.remove(q);

            // generate q's 8 successors and set their parents to q
            // if successor is the goal, stop the search
            if (isGoal(q)) {
                System.out.println("search completed- goal found");
                MyNode i = this.getGoalNode();
                while (i.getParent() != null) {
                    toReturn.add(i);
                    i = q.getParent();
                }
                return toReturn;
            }

            closedList.add(q);
            ArrayList<MyNode> successors = q.getSuccessors();

            for (MyNode node : successors) {
                if (closedList.contains(node)) {
                    continue;
                }

                node.setParent(q);

                /*
                 * successor.g = q.g + distance between successor and q
                 * successor.h = distance from goal to successor
                 * successor.f=successor.g + successor.h
                 */

                double g = q.getG()
                        + Search.distFrom(q.getLat(), q.getLon(),
                                node.getLat(), node.getLon());

                double h = Search.distFrom(this.getGoalNode().getLat(), this
                        .getGoalNode().getLon(), q.getLat(), q.getLon());

                node.setG(g);
                node.setH(h);

                node.setF(g + h);

                // if a node with the same position as successor is in the OPEN
                // list
                // has a lower f than successor, skip this successor

                int openIndex = openList.indexOf(node);
                int closedIndex = closedList.indexOf(node);

                if (openIndex > -1) {

                    if (openList.get(openIndex).compareTo(node) == -1)
                        continue;

                }

                // if a node with the same position as successor is in the
                // CLOSED list
                // which has a lower f than successor, skip this successor
                if (closedIndex > -1) {
                    if (closedList.get(closedIndex).compareTo(node) == -1)
                        continue;

                }

                if (openIndex > -1)
                    openList.remove(openIndex);
                Collections.sort(openList);

                if (closedIndex > -1)
                    closedList.remove(closedIndex);

                openList.add(node);
                Collections.sort(openList);

            }
            closedList.add(0, q);

        }
        return toReturn;
    }
这些节点具有以下属性:

    node [id=21295291, lat=52.4737031, lon=-1.8747258]
node [id=119126329, lat=52.4701337, lon=-1.8716235]
代码


断开内部循环(for),但也有外部while循环。您可以使用“return;”此处不是“break”(或标记为break)。

您尝试过使用调试器吗?您在循环中调用了goalFound(),因此很明显,它会在找到目标后继续循环。该系统。退出(0)会中断每个循环。当然它是有效的,但我强烈反对它,这是一个廉价的修复方案,可能会带来问题。请您更新您的问题正文,因为您声称有一个“getRoute()”方法,但很明显,您没有在代码段中使用它。@SotiriosDelimanolis是的-我可以看到他们一遍又一遍地将自己设置为家长,非常奇怪。@tiago7请你给我举个例子,说明我如何能正确地打破一切?这已经给我带来了问题,因为我不希望搜索结束成为我程序的结束。我还有一个例子,我可以展示,即使我返回时也会做同样的事情。我已经添加了它。@MJB另外,你能在提供输入数据的地方发布你的
main
?因为我怀疑你的
I.getParent()!=null
条件,正如您所说,它将在此处继续循环。这只意味着你将有多个父母在那里?添加了@hagubear和更多的信息。
    node [id=21295291, lat=52.4737031, lon=-1.8747258]
node [id=119126329, lat=52.4701337, lon=-1.8716235]
  goalFound();
  break;