我正在研究一个程序,这是一个具有用户界面的抛射运动模拟。我得到一个StackOverflow错误,它似乎发生在我试图为我的按钮和文本字段创建我的动作监听器。我知道stackoverflow错误与永远不会退出的递归有关,但我没有在我的代码中看到它发生的地方。
我决定在我的程序中使用线程,因为我所拥有的耗时的活动减慢了程序。所以我有一个线程来处理模拟的所有计算。
代码很长,但这里是它的结构。
public class SimulationGUI implements ActionListener, Runnable
{
//Create object references for window, panels, text fields, buttons, and labels.
SimulationGUI()
{
//Here I instantiate all my buttons, textfields, labels,
//and basically set up the user interface.
createListeners(); //This calls a method that creates my action listeners
}
public void actionPerformed(ActionEvent e)
{
Thread thread = new Thread(this);
thread.start(); // this calls the method run()
}
public void run()
{
//Here, I get the text for the variables
//calculations are performed for the projectile motion
//I also edit three top level text fields using .setText()
}
public void createListeners()
{
//Add action listeners for each text field
ActionListener angleList = new SimulationGUI();
angleText.addActionListener(angleList);
.....
}
public static void main(String[] args)
{
new SimulationGUI();
}
}
我猜我将不得不在一个新的线程中创建和添加动作监听器,但我不完全确定。以下是我得到的错误:
Exception in thread "main" java.lang.StackOverflowError
at java.awt.Insets.<init>(Unknown Source)
at sun.awt.windows.WToolkit.getScreenInsets(Native Method)
at sun.awt.windows.WToolkit.getScreenInsets(Unknown Source)
at java.awt.Window.init(Unknown Source)
at java.awt.Window.<init>(Unknown Source)
at java.awt.Frame.<init>(Unknown Source)
at javax.swing.JFrame.<init>(Unknown Source)
at SimulationGUI.<init>(SimulationGUI.java:24)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
.....
是的,你得到了一个无限循环。这是导致问题的代码部分:
SimulationGUI()
{
createListeners();
}
public void createListeners()
{
ActionListener angleList = new SimulationGUI();
angleText.addActionListener(angleList);
}
知道怎么了吗?这两个方法都无条件地相互调用,并且在剩余的时间内(或者至少在堆栈满之前)都会这样做。证据在堆栈跟踪中:
at SimulationGUI.<init>(SimulationGUI.java:24)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.<init>(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
看到这些方法是如何相互调用的了吗?您可能想要更像这样的内容:
SimulationGUI()
{
createListeners();
}
public void createListeners()
{
angleText.addActionListener(this);
}
Exception in thread "main" java.lang.StackOverflowError
at java.awt.Insets.(Unknown Source)
at sun.awt.windows.WToolkit.getScreenInsets(Native Method)
at sun.awt.windows.WToolkit.getScreenInsets(Unknown Source)
at java.awt.Window.init(Unknown Source)
at java.awt.Window.(Unknown Source)
at java.awt.Frame.(Unknown Source)
at javax.swing.JFrame.(Unknown Source)
at SimulationGUI.(SimulationGUI.java:24)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
at SimulationGUI.(SimulationGUI.java:124)
at SimulationGUI.createListeners(SimulationGUI.java:211)
从你的代码和堆栈转储来看,我看到的直接问题是:每次你的SimulationGUI构造函数被调用时,就会调用createlistener,这会创建另一个SimulationGUI,这个SimulationGUI会调用createlistener,然后创建另一个SimulationGUI等等。除此之外,每次调用createlistener时,都会启动一个新线程。