AWTEventMulticaster.mouseEntered()中导致无限递归的原因是什么?

3
我已经开始使用JFrame一段时间了,自从我开始使用Mouselistener(或任何事件监听器)以来,事情大约会顺利进行2分钟左右。然后我会收到大量重复的错误,程序仍然可以运行,但我将无法使用任何事件监听器。错误基本上是这样的:...(无法及时捕获顶部行,但类似于"AWT-EventQueue-0"线程中的异常java.lang.StackOverflowError) (随后跟着)
at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
    at java.awt.AWTEventMulticaster.mouseEntered(AWTEventMulticaster.java:282)
...

重复了数百行,其中mouseEntered可能是任何事件侦听器之一。

我已经花了很多时间检查所有整数是否过高(找到一个并修复了它,但仍然发生)。我还在各个地方检查调用自身的值,但这并没有太多意义,因为它发生在大约2分钟后。

我认为这与任何特定代码无关,只需告诉我它的含义以及如何修复它。


2
如果您能发布MouseListener的代码以及它的使用方式,那将会很有帮助。 - Bala R
1
我不认为这与任何特定的代码有关 -- 你怎么知道这一点? 你采取了哪些调试步骤证明了这个声明? 在那之前,你有一个简单的错误,代码将帮助我们解决它。 是否所有的 Swing 代码都在 EDT 上被调用? 是否存在递归? 编辑:实际上,我会推断出存在递归,无论你是否看到它。 同样,您的代码可以为我们回答这个问题。 - Hovercraft Full Of Eels
好的,我猜你已经解决了这个问题。祝你好运。 - Hovercraft Full Of Eels
5个回答

2
我猜最有可能的原因是您已经将一个组件放入了自身(直接或间接地)。

1

如上所述,你的代码中有一个简单的bug,直到你展示给我们这段代码,我怀疑我们除了猜测之外无法做任何事情。话虽如此,我的猜测是你可能在递归中进行操作,可能是无意识地通过在MouseListener本身内部向GUI组件添加MouseListener。

不管怎样,为了你自己和我们所有人的利益,请展示相关的代码,因为大多数人都不喜欢猜测。


0

我曾经遇到过类似的情况,虽然问题可能需要更好地表述,但是Hovercraft[^s]+?s给了一个很好的提示(递归),这对我很有帮助。

这种问题可能不会在简单的代码中出现。至少在我的情况下,它发生在一个复杂的应用程序中,其中包含许多嵌套的Swing组件,包括封装在专有类中的JInternalFrames等。

在我们的情况下,尚未完全解决,我们对鼠标监听器的管理很差(在面板的每个组件上添加了很多监听器来处理相同的上下文菜单,而不是具有更全局的管理),并且根据用户操作添加和删除了监听器。
无论如何,我怀疑我们在某个地方添加了很多监听器(真的很多!)而没有正确地删除它们。在正常操作中,我们不必将它们删除,当组件被处理时,它会自动完成,但是在这里,监听器被添加并且没有处理组件。而堆栈溢出可能只是在非常深的堆栈上进行迭代...

我正在分析代码,以避免所有这些无用的监听器添加(也许在添加之前检测是否存在?)。无论如何,在极小的机会下,上述分析可能对遇到类似情况的人有用,我在这里公开它。


0
根据我的经验,重复将给定控件添加到同一父级,然后调用doLayout()可能会导致AWTEventMulticaster出现stackoverflow,但这可能只是特定Java版本(jdk_1.6.18)中的错误。而这种重新添加操作可能看起来毫无意义,但却是重用组件的副作用。
AWTEventMulticaster用于控制移动/调整大小和KeyEvent处理的传播。请检查相关操作。

0
我曾经遇到过同样的问题... 在我的代码中,动态地向一个对象实例添加和删除鼠标监听器,但是做法不正确... 结果就是产生了你所描述的相同错误。 一旦删除了添加和删除鼠标监听器的操作,一切都恢复正常了。 显然,解决这个问题的方法是正确地添加和删除监听器。
gossip-automation.

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接