Difference between shutdown and shutdownNow of Executor Service

Javajava.util.concurrent

Java Problem Overview


I want to know the basic difference between shutdown() and shutdownNow() for shutting down the Executor Service?

As far as I understood:

shutdown() should be used for graceful shutdown which means all tasks that were running and queued for processing but not started should be allowed to complete

shutdownNow() does an abrupt shut down meaning that some unfinished tasks are cancelled and unstarted tasks are also cancelled. Is there anything else which is implicit/explicit that I am missing?

P.S: I found another question on How to shutdown an executor service related to this but not exactly what I want to know.

Java Solutions


Solution 1 - Java

In summary, you can think of it that way:

  • shutdown() will just tell the executor service that it can't accept new tasks, but the already submitted tasks continue to run
  • shutdownNow() will do the same AND will try to cancel the already submitted tasks by interrupting the relevant threads. Note that if your tasks ignore the interruption, shutdownNow will behave exactly the same way as shutdown.

You can try the example below and replace shutdown by shutdownNow to better understand the different paths of execution:

  • with shutdown, the output is Still waiting after 100ms: calling System.exit(0)... because the running task is not interrupted and continues to run.
  • with shutdownNow, the output is interrupted and Exiting normally... because the running task is interrupted, catches the interruption and then stops what it is doing (breaks the while loop).
  • with shutdownNow, if you comment out the lines within the while loop, you will get Still waiting after 100ms: calling System.exit(0)... because the interruption is not handled by the running task any longer.

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...");
}

Solution 2 - Java

  • shutdown():

To terminate the threads inside the ExecutorService you call its shutdown() method. The ExecutorService will not shut down immediately, but it will no longer accept new tasks, and once all threads have finished current tasks, the ExecutorService shuts down. All tasks submitted to the ExecutorService before shutdown() is called, are executed.

  • shutdownNow():

If you want to shut down the ExecutorService immediately, you can call the shutdownNow() method. This will attempt to stop all executing tasks right away, and skips all submitted but non-processed tasks. There are no guarantees given about the executing tasks. Perhaps they stop, perhaps the execute until the end. It is a best effort attempt.

Solution 3 - Java

From the javadocs:

> void shutdown > > Initiates an orderly shutdown in which previously submitted tasks are > executed, but no new tasks will be accepted.

> List<Runnable> shutdownNow() > > Attempts to stop all actively executing tasks, halts the processing of > waiting tasks, and returns a list of the tasks that were awaiting > execution. > > There are no guarantees beyond best-effort attempts to stop > processing actively executing tasks. > > For example, typical implementations will cancel via > Thread.interrupt(), so any task that fails to respond to interrupts > may never terminate. > > Returns: list of tasks that never commenced execution

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionGeekView Question on Stackoverflow
Solution 1 - JavaassyliasView Answer on Stackoverflow
Solution 2 - JavaAhmed MANSOURView Answer on Stackoverflow
Solution 3 - JavafmucarView Answer on Stackoverflow