gpt4 book ai didi

java - 自定义事件处理中的堆栈溢出

转载 作者:太空宇宙 更新时间:2023-11-04 07:05:00 25 4
gpt4 key购买 nike

我尝试使用一个非常简单的JAVA示例(我是新手)来处理事件;这是一个游戏骨架(比如国际象棋,有两个玩家,白人和黑人)这是源代码:

//---------------------------------------------------------
// Game.java

package chess;

public class Game {

private static Player p1;
private static Player p2;
private static Board b;

public static void main(String[] args) {
b = new Board();
p1 = new Player(b, "white");
p2 = new Player(b, "black");

p1.MakeMove();
}
}

//---------------------------------------------------------
// Board.java

package chess;

import java.util.ArrayList;

public class Board {

int num;
private ArrayList<NextMoveListener> listeners = new ArrayList<NextMoveListener>();

public Board() {
num = 0;
}

public void addListener(NextMoveListener nml) {
listeners.add(nml);
}

void LastMove() {
System.out.println("Game Over!");
}

void NextMove(NextMoveEvent e) {
if (e.finished) {
LastMove();
} else {
for (NextMoveListener nml : listeners) {
if (nml != e.getSource()) {
nml.MakeMove();
}
}
}
}
}

//---------------------------------------------------------
// Player.java

package chess;

interface NextMoveListener {
public void MakeMove();
}

public class Player implements NextMoveListener {

private String name;
private Board b;
private int nMove;
private NextMoveEvent evt;

Player(Board b, String nome) {
this.nMove = 0;
this.b = b;
this.name = nome;
this.evt = new NextMoveEvent(this);
b.addListener(this);
}

@Override
public void MakeMove() {
System.out.println("Player: " + name + ", move: " + (++nMove));
evt.setFinished(nMove == 1000);
b.NextMove(evt);
}
}

//---------------------------------------------------------
// NextMoveEvent.java

package chess;

import java.util.EventObject;

public class NextMoveEvent extends EventObject {

boolean finished;

public NextMoveEvent(Object source) {
super(source);
}

public void setFinished(boolean finished) {
this.finished = finished;
}
}

显然里面没有真正的游戏,它只是两个玩家之间交换事件的一个例子;每个玩家大约 1000 步时效果很好;如果我增加该数字,则会出现堆栈溢出错误。我看不到我的错误!在我看来,调用 MakeMove() 方法时没有在堆栈上保留任何空间,但它仍然崩溃。

最佳答案

当您从另一个方法内部调用一个方法时,Java 需要跟踪第一个方法的状态,直到第二个方法返回。因此,如果 A 调用 B,而 B 又调用 C,则我有一个方法 A > B > C 的“堆栈”,我需要记住其状态。

Java 允许的嵌套方法层数是有限的。因此,如果您对这样的嵌套方法太深入,就会发生异常(堆栈溢出)。

一种解决方案是将递归方法更改为循环。让 Player.MakeMove() 返回 NextMoveEvent,而不是直接调用 Board.NextMove()。然后,让开发板继续在循环中的每个监听器上调用 MakeMove(),直到返回已设置 finished 的事件。

关于java - 自定义事件处理中的堆栈溢出,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21561087/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com