Java,正确使用wait和notify来暂停从另一个线程执行线程

时间:2013-09-02 19:50:49

标签: java multithreading swing

我在尝试从另一个线程暂停线程执行时遇到问题。我已经阅读了java文档和一些堆栈溢出示例,但似乎仍然有点遗失。

许多案件就像我的;我有一个gui,它产生一个线程来做一些工作,所以它可以保持对用户的响应。在某些时候,用户会做一些事情,这样就可以在执行下一个语句之前停止工作线程。然后过了一段时间,继续工作。

我已阅读wait的{​​{1}}和notify文档,这似乎是上述问题的简短答案(?)。

根据我的IDE(netbeans)告诉我的内容,我必须在同步块中调用Threadswait

所以这就是我按下开始暂停按钮时在JFrame中所拥有的内容。 notify是我要暂停的automator对象。它在我的JFrame中声明为Threadstatic final只是第一次按下firstRunDone时的标记,因此m_jbStartPause可以启动而不会被通知。

automator

我的问题是当我第一次尝试暂停线程时。我可以点击开始并且自动变速器启动,但是当我点击暂停时,所有发生的事情都是JFrame冻结并且自动变速器继续执行其工作。

我使用同步错误吗? OnStartPauseButton() { synchronized(automator) { if(!running) { this.m_jbStartPause.setText("Pause"); running = true; if(firstRunDone) automator.notify(); else automator.start(); firstRunDone = true; } else { this.m_jbStartPause.setText("Start"); running = false; try { automator.wait(); } catch (InterruptedException ex) {} } } } 是否需要任何处理代码?

2 个答案:

答案 0 :(得分:1)

  • 您最好使用SwingUtilities.invokeLater来更新UI而不是使用工作线程

  • 如果您需要“取消”您的主题,则需要将“运行”标记设为易变

  • 而不是使用“已同步”,我建议使用ReentrantLock及其条件

答案 1 :(得分:1)

FOllowing line是问题

try { automator.wait(); }  catch (InterruptedException ex) {}

这将导致线程(您的GUI)线程不等待自动机。 JAVA文档说

  

wait()..使当前线程等到另一个线程调用   此对象的notify()方法或notifyAll()方法,或一些   其他线程会中断当前线程或一定数量的线程   实时已经过去了

这就是为什么你的JFrame似乎被冻结并且automator继续运行的原因。您需要在automator中构建一个机制来轮询标志的状态以查看它是否需要继续其工作......并且您的GUI线程应该更改标志的状态以停止自动机的工作。