我有一个简单的带有gui的JAVA程序,它只是递增int变量并在JLabel中显示它的值。 我创建了一个新的线程,用于正确(线程安全)更新JLabel,方法是在其中使用Runnable类调用EventQueue.invokeLater(),该方法只是运行方法
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
label.setText("" + number);
}
});
当我运行程序时,正如预期的标签编号从1开始迅速增长到约5000但随后它开始变慢,我开始看到这样的标签更新,如100255,173735,235678以及它们之间的大停顿阻止了GUI。
但是当我在不使用EventQueue.invokeLater()的情况下进行编译时,只需直接调用label.setText("" + number);
一切正常且完美,我可以看到我的标签的每个数字如何变化非常快。但当然我知道在这种情况下我的方法不是线程安全的。
有什么问题?在我看来,EventQueue工作缓慢或其他什么。
答案 0 :(得分:3)
可能是事件队列被阻塞了。您可能希望查看合并事件以在排队事件的速度快于排队和执行事件时删除冗余条目。
每次将事件添加到队列时,都会查询现有事件以查看它们是否将新事件与自身合并。当队列备份时,必须查询越来越多的事件,并且系统逐渐进一步落后。这对于鼠标事件很有用,但在这样的简单(和人工)情况下,它可能是有害的。
话虽如此,我依旧回忆起GUI代码经过优化,不会尝试合并不会覆盖适当方法的事件,因此您的问题可能只是一个简单的积压。
您可以创建一个自定义事件来设置组件上的文本,并为其实现合并,而不是直接调用setText
,而是使用该事件,以便在任何给定时间只有最新文本处于待处理状态。如果执行此操作并且您希望根据先前设置的内容设置文本,则最好保留该值并始终从中设置GUI小部件,而不是使用getText
调用GUI小部件的当前值。否则合并就困难得多。