使用较大数量时出现Stackoverflow错误

时间:2019-02-12 02:17:08

标签: java

我正在尝试使用递归编写a *路径查找算法,但遇到了麻烦。该代码找到了更小的距离的路径,但是当我尝试使用更大的数字时,会出现堆栈溢出错误。我是递归的新手,所以肯定有我做错了什么,但我无法弄清楚。我有退出条件,它在较小的数字上也能正常工作,因此除非算法本身有问题,否则我不知道该怎么办。问题发生在执行递归的findAlgorithm()方法中。

算法:

Node[][]nodes;
ArrayList<Node> options = new ArrayList<Node>();
ArrayList<Node> path = new ArrayList<Node>();
private int x, y, endX, endY;
Node endNode;

public Algorithm(Node[][]nodes) {
    this.nodes = nodes;
    setStartPosition();
    findEndPosition();
}

public ArrayList<Node> getPath() {

    Node node = endNode;

    while(node.hasParent()) {
        path.add(node);
        node = node.getParent();
    }

    return path;

}

public void findPath() {

    if(x!=endX || y!=endY) {
        getSurroundingNodes();
        if(options.size()>0) {
            Node lowestVal = options.get(0);
            for(Node i : options) {
                if(i.getValue()<lowestVal.getValue()) {
                    lowestVal = i;
                }
                else if(i.getValue() == lowestVal.getValue()) {
                    if(i.getEndDistance()<lowestVal.getEndDistance()) {
                        lowestVal = i;
                    }
                }
            }
            x = lowestVal.getX();
            y = lowestVal.getY();
            lowestVal.setTaken();
            options.remove(lowestVal);
            findPath();
        }
    }
    else {
        System.out.println("Made it");
    }

}

private void getSurroundingNodes() {

    Node parent = nodes[y][x];
    for(int i=y-1;i<y+2; i++) {
        for(int z=x-1;z<x+2; z++) {

            if(i>=0&&z>=0&&i<nodes.length&&z<nodes[i].length) {
                Node node = nodes[i][z];
                double endDistance = Math.sqrt((i-endY)*(i-endY)+(z-endX)*(z-endX));
                double startDistance = parent.getStartDistance()+Math.sqrt((i-y)*(i-y)+(z-x)*(z-x));
                double value = endDistance+startDistance;
                if(!node.isWall()&&!node.isTaken()) {
                    if(!options.contains(node)) {
                        node.setParent(parent);
                        node.setX(z);
                        node.setY(i);
                        node.setStartDistance(startDistance);
                        node.setEndDistance(endDistance);
                        node.setValue(value);
                        options.add(node);
                    }
                    else {
                        if(node.getValue()<value) {
                            //do nothing
                        }
                        else if (node.getValue() == value) {
                            if(node.getEndDistance()<=endDistance) {
                                //do nothing
                            }
                            else {
                                node.setParent(parent);
                                node.setX(z);
                                node.setY(i);
                                node.setStartDistance(startDistance);
                                node.setEndDistance(endDistance);
                                node.setValue(value);
                                options.add(node);
                            }
                        }
                        else {
                            node.setParent(parent);
                            node.setX(z);
                            node.setY(i);
                            node.setStartDistance(startDistance);
                            node.setEndDistance(endDistance);
                            node.setValue(value);
                            options.add(node);
                        }
                    }
                }
            }
        }
    }

}

private boolean findEndPosition() {

    for(Node[] i : nodes) {
        for(Node z : i) {
            if(z.isEnd()) {
                endX = z.getX();
                endY = z.getY();
                endNode = z;
                return true;
            }
        }
    }
    return false;       
}

private boolean setStartPosition() {

    for(Node[] i : nodes) {
        for(Node z : i) {
            if(z.isStart()) {
                z.setTaken();
                x = z.getX();
                y = z.getY();
                return true;
            }
        }
    }
    return false;       
}

节点:

private int x, y;
private boolean wall, start, end, taken, hasAParent;
private double endDistance, startDistance, value;
private Node parent = null;

public Node() {
    wall=false;
    start=false;
    end=false;
    taken=false;
    hasAParent = false;
}

public boolean hasParent() {
    return hasAParent;
}

public int getX() {
    return x;
}

public void setX(int x) {
    this.x = x;
}

public int getY() {
    return y;
}

public void setY(int y) {
    this.y = y;
}

public boolean isWall() {
    return wall;
}

public void setWall() {
    wall = true;
    end = false;
    start = false;
}

public boolean isStart() {
    return start;
}

public void setStart(int x, int y) {
    this.x = x;
    this.y = y;
    start = true;
    end = false;
    wall = false;
    endDistance=0.0;
    startDistance=0.0;
    value=0.0;
}

public boolean isEnd() {
    return end;
}

public void setEnd(int x, int y) {
    this.x = x;
    this.y = y;
    end = true;
    start = false;
    wall = false;
    hasAParent = true;
}

public boolean isTaken() {
    return taken;
}

public void setTaken() {
    taken = true;
}

public double getEndDistance() {
    return endDistance;
}

public void setEndDistance(double endDistance) {
    this.endDistance = endDistance;
}

public double getStartDistance() {
    return startDistance;
}

public void setStartDistance(double startDistance) {
    this.startDistance = startDistance;
}

public double getValue() {
    return value;
}

public void setValue(double value) {
    this.value = value;
}

public Node getParent() {
    return parent;
}

public void setParent(Node parent) {
    this.parent = parent;
    hasAParent = true;
}

0 个答案:

没有答案