【问题标题】:Why do we need to use awaitTermination but not just shutdownNow()?为什么我们需要使用 awaitTermination 而不仅仅是 shutdownNow()?
【发布时间】:2020-08-26 22:59:12
【问题描述】:

我正在遵循 oracle 推荐的标准流程来关闭执行程序服务。这是推荐的代码:

 void shutdownAndAwaitTermination(ExecutorService pool) {
   pool.shutdown(); // Disable new tasks from being submitted
   try {
     // Wait a while for existing tasks to terminate
     if (!pool.awaitTermination(60, TimeUnit.SECONDS)) {
       pool.shutdownNow(); // Cancel currently executing tasks
       // Wait a while for tasks to respond to being cancelled
       if (!pool.awaitTermination(60, TimeUnit.SECONDS))
           System.err.println("Pool did not terminate");
     }
   } catch (InterruptedException ie) {
     // (Re-)Cancel if current thread also interrupted
     pool.shutdownNow();
     // Preserve interrupt status
     Thread.currentThread().interrupt();
   }
 }

我阅读了shutdown()awaitTerminationshutdownNow() 的描述;

我了解
shutdown() 只会停止提交新线程。

awaitTermination 等待正在运行的线程被关闭。如果执行完成、超时或当前线程中断之一,则返回一个值。

shutdownNow() 使用Thread.interrupt() 来中断线程。

我的问题是,如果我确定我的线程只使用sleep,它可以被Thread.interrupt() 打断。像oracle推荐的那样调用awaitTermination还有价值吗?

我知道shutdownNow() 可能有机会不关闭线程,但为什么我们不能继续执行类似的操作来强制停止线程,然后查看是否还有未停止的线程?

pool.shutdown();
pool.shutdownNow();
  try {
     if (!pool.awaitTermination(60, TimeUnit.SECONDS)) {
           System.err.println("Pool did not terminate");
     }
   } 

【问题讨论】:

  • 噢噢噢!!!!是的,你是对的,所以我的代码做的不仅仅是睡眠,它首先睡眠一段时间然后开始做其他事情。在这种情况下,当我的代码在做其他事情时,如果我不使用 awaitTermination,并且如果其他事情运行了很长时间,它不会立即终止,对吗?

标签: java thread-safety executorservice


【解决方案1】:

“标准进程”只是试图优雅地处理关闭,前提是在不需要时不中断线程。

首先它停止接受新的任务提交并让正在进行的任务完成它们的工作。只有当它们没有在宽限期内完成时,它才会进行强制终止。

【讨论】:

  • 我的目的是在我拨打shutdownAndAwaitTermination() 时立即停止。但从建议来看,它仍然允许宽限时间来完成正在进行的任务。如果我现在只想停止,是否仍然需要调用第一个 awaitTermination?
  • 从之前的评论中,我意识到我的线程不仅会休眠,而且里面还有其他进程,所以如果我在我的线程处于其他进程时触发 shutdownNow,它不会正确终止?对吗?
  • @MalcolmLiu 只要您不需要文档建议的额外工作,您的关闭方法就非常好。您需要检查您的用例并决定是否可以跳过它。请记住,一旦您调用shutdownNowInterruptedException 将在这些线程中抛出),您的线程很有可能会被中止。
  • 谢谢@jannis,这真的帮助我清理了这些东西。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-11-24
  • 1970-01-01
  • 1970-01-01
  • 2013-02-14
相关资源
最近更新 更多