【问题标题】:java swing, necessary calls in main method [duplicate]java swing,main方法中的必要调用[重复]
【发布时间】:2013-08-28 00:26:50
【问题描述】:

在准备考试时,我偶然发现了 Java 图形中的一些我不太清楚的线条。所以我开始浏览并检查其他一些程序,它们没有这些行。

示例:

public static void main(String[] args){
  SwingUtilities.invokeLater(new Runnable(){//unknown
  public void run(){                        //lines
  JPanel panel = new DrawingPanel();
  ...
}

现在我知道 Runnable 和 run 必须处理线程,但我不知道这两行为什么以及如何工作

【问题讨论】:

  • 请查看Concurrency in Swing。 Java Docs 可以更好地解释这一点:-)
  • Swing 的一个关键是所有 Swing 调用都应该在单个线程上进行,即事件调度线程,包括启动 GUI 的代码。您正在做的事情(如果您查找 SwingUtilities,API 会告诉您正在做的事情)正在将 Runnable 排队到此事件线程上。
  • 这个问题是一个副本的副本,它已经是一个副本。在询问之前先搜索一下!
  • 是的,投票以重复结束

标签: java swing awt


【解决方案1】:

Swing 对象只能从在处理重绘、GUI 事件等的闭环中运行的 Swing 线程中访问。当您的应用程序启动时,它会在普通线程(不是 Swing 线程)中启动。对您来说看起来很奇怪的行使用SwingUtilities 来执行 DrawingPanel 构造函数,并且可能在 Swing 线程中执行更多代码。

直接从主线程实例化第一个 GUI 框架的代码如果真的是第一个调用的方法(如预期的那样),也可以在实践中工作。然而,如果不同的调用等,它是“根本错误”的方法,以后可能无法在不同的机器下工作。

【讨论】:

    【解决方案2】:

    Swing 是一个单线程框架。与 UI 的所有交互和更新都应在事件调度线程的上下文中执行。

    Java 不保证 main 在 EDT 内执行(我相信他们通常将其称为主线程)。因此,您需要确保您的任何 UI 代码首先同步到 Event Dispatching Thread。

    SwingUtilities.invokeLater,委托给EventQueue.invokeLater。这基本上将Runnable 实例发布到事件队列中,由事件调度线程处理。

    在未来的某个时间,Runnable 会从队列中弹出,run 方法会在 EDT 内执行

    详情请见Initial Threads

    您还可以查看The Single Thread Rule in SwingEvent-Dispatching Thread Rules for Swing UIs 了解更多信息

    【讨论】:

    • “保证不会在 EDT 内执行”... 除非您指定 -XstartOnFirstThread,这是在 Cocoa 上运行 SWT 的要求。
    • @MarkoTopolnik 1- 不保证支持 X 参数 2- 我在可用参数列表中看不到 XstartOnFirstThread(诚然,我正在检查 Windows 版本)3 - 不要对程序的状态做任何假设仍然更安全(是的,你可以检查EventQueue#isEventDispatchingThread,但无论如何你仍然需要invokeLater 调用......
    • 这是特定于 OS X 的问题,是的。但是,这个反例确实影响了“保证不会在 EDT 内执行”的声明。显然,没有任何保证(如果“保证”是指 JVM 规范)。
    • @MarkoTopolnik 无法保证执行应用程序的用户将使用-X 参数,或者应用程序在支持它的环境中开始执行,或者-X 参数可用。正如我所说,是的,你可以检查isEventDispatchingThread,但无论如何你仍然需要提供invokeLater......恕我直言,假设最坏的情况更简单
    • 您编辑的措辞肯定更好地反映了现实:不能保证main 将或赢得t run on the EDT. Assume the worst, by all means, but dont 依靠实际得到保证的最坏情况:)跨度>
    猜你喜欢
    • 2016-11-13
    • 2011-06-18
    • 1970-01-01
    • 2014-03-26
    • 2020-12-17
    • 2012-09-28
    • 1970-01-01
    • 2020-06-20
    • 1970-01-01
    相关资源
    最近更新 更多