1.2.4 响应更灵敏的用户界面
传统的GUI应用程序通常都是单线程的,从而在代码的各个位置都需要调用poll方法来获得输入事件(这种方式将给代码带来极大的混乱),或者通过一个“主事件循环(Main Event Loop)”来间接地执行应用程序的所有代码。如果在主事件循环中调用的代码需要很长时间才能执行完成,那么用户界面就会“冻结”,直到代码执行完成。这是因为只有当执行控制权返回到主事件循环后,才能处理后续的用户界面事件。
在现代的GUI框架中,例如AWT和Swing等工具,都采用一个事件分发线程(Event Dispatch Thread, EDT)来替代主事件循环。当某个用户界面事件发生时(例如按下一个按钮),在事件线程中将调用应用程序的事件处理器。由于大多数GUI框架都是单线程子系统,因此到目前为止仍然存在主事件循环,但它现在处于GUI工具的控制下并在其自己的线程中运行,而不是在应用程序的控制下。
如果在事件线程中执行的任务都是短暂的,那么界面的响应灵敏度就较高,因为事件线程能够很快地处理用户的动作。然而,如果事件线程中的任务需要很长的执行时间,例如对一个大型文档进行拼写检查,或者从网络上获取一个资源,那界面的响应灵敏度就会降低。如果用户在执行这类任务时触发了某个动作,那么必须等待很长时间才能获得响应,因为事件线程要先执行完该任务。更糟糕的是,不仅界面失去响应,而且即使在界面上包含了“取消”按钮,也无法取消这个长时间执行的任务,因为事件线程只有在执行完该任务后才能响应“取消”按钮的点击事件。然而,如果将这个长时间运行的任务放在一个单独的线程中运行,那么事件线程就能及时地处理界面事件,从而使用户界面具有更高的灵敏度。
Get Java并发编程实战 now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.