我很好奇以下创建 Swing 窗口的方法之间的区别:
- 在 main() 中使用 java.awt.EventQueue.invokeLater();
- 在 main() 中使用 SwingUtilities.invokeLater();
- 根本不关心线程,只需实例化 JFrame 子类并从 main 调用 setVisible(true) 而不将其包装在 Runnable 中;无论如何,这似乎有效。
谢谢。
SwingUtilities.invokeLater
只是打电话EventQueue.invokeLater
。后者是在 Java 1.2 中引入的。在此之前,Swing 有一个 hack,它重新粉刷了一个窗口以进入 EDT。我建议这java.awt.EventQueue
是这种方法的合乎逻辑的地方,也是明智的选择。但是,Swing 和 AWT 之间的关系严重混乱。
很少需要子类化JFrame
,这通常是不好的做法。但是不好的做法是 Swing 的标准。像这样运行多线程可能会遇到问题,尽管您可能会在自己的机器上侥幸逃脱。您可以做的最糟糕的事情是在 EDT 上进行一些初始化,在主线程上进行一些初始化(有一段时间,FindBugs(所有程序的)是否会在单个硬件线程机器上启动是 50/50)。
线程要记住的是,“似乎有效”与“在所有情况下都可以证明有效”不同。
基本规则是您不应该在事件线程之外创建 Swing/操作组件,并且应用程序的主线程在“事件线程之外”。所以在你的应用程序启动代码中,你应该在invokeLater() 中创建你的主窗口。
如果您使用 Swing 进行编程,我会使用 invokeLater() 的 SwingUtilities 版本。尽管我认为在当前的实现中,一个只是调用另一个,但我想这在未来可能会改变。