我想知道shutdown()shutdownNow()之间用于关闭Executor Service的基本区别吗?

据我了解:
shutdown()应该用于正常关机,这意味着所有正在运行并排队等待处理但尚未启动的任务都应被允许完成
shutdownNow()会突然关闭,而会突然关闭,这意味着一些未完成的任务会被取消,未启动的任务也会被取消。还有其他我不知道的隐式/显式信息吗?

附注:我在How to shutdown an executor service上发现了另一个与此相关的问题,但并不是我想知道的确切问题。

最佳答案

总之,您可以这样考虑:

  • shutdown()只会告诉执行者服务它不能接受新任务,但是已经提交的任务将继续运行
  • shutdownNow()将执行相同的操作,并且将尝试通过中断相关线程来取消已经提交的任务。请注意,如果您的任务忽略了中断,shutdownNow的行为将与shutdown完全相同。

  • 您可以尝试下面的示例,并用shutdown替换shutdownNow以更好地理解不同的执行路径:

    shutdown
  • ,输出为Still waiting after 100ms: calling System.exit(0)...,因为正在运行的任务是,而并未中断,并继续运行。
  • shutdownNow
  • ,输出为interruptedExiting normally...,因为正在运行的任务被中断,捕获了中断,然后停止了正在执行的操作(中断了while循环)。
  • shutdownNow,如果在while循环中注释掉各行,则会得到Still waiting after 100ms: calling System.exit(0)...,因为正在运行的任务不再处理中断。

  • public static void main(String[] args) throws InterruptedException {
        ExecutorService executor = Executors.newFixedThreadPool(1);
        executor.submit(new Runnable() {
    
            @Override
            public void run() {
                while (true) {
                    if (Thread.currentThread().isInterrupted()) {
                        System.out.println("interrupted");
                        break;
                    }
                }
            }
        });
    
        executor.shutdown();
        if (!executor.awaitTermination(100, TimeUnit.MICROSECONDS)) {
            System.out.println("Still waiting after 100ms: calling System.exit(0)...");
            System.exit(0);
        }
        System.out.println("Exiting normally...");
    }
    

    10-08 00:26