Card 06/ 08

GotchaDifficulty: Advanced1 min

Daemon Threads: Why a Java Program Does Not Exit

main has finished, the completion message is printed, and the process keeps running.

The Java virtual machine exits when its last non-daemon thread finishes. Threads are non-daemon by default, so one that runs a loop forever keeps the whole process alive after main has returned. A daemon thread is one marked as background work that must not keep the process alive.

main reaches its last line and prints the completion message. The process does not end, and nothing in the logs says why:

java
Thread poller = new Thread(() -> {
    while (true) {
        checkForWork();
        try {
            Thread.sleep(1_000);
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
            return;
        }
    }
});

poller.start();
System.out.println("started");

main is one non-daemon thread and the poller is another. main finished; the poller never does, so the process stays alive with nothing useful left to do.

What the daemon flag changes
Compared onNon-daemon, the defaultDaemon
Keeps the process aliveYesNo
Killed at exitNo: the machine waits for itYes, wherever it had got to
SuitsWork that must finishBackground polling, monitoring, clean-up
java
poller.setDaemon(true);
poller.start();
must be set before start(), or it throws

For work that must finish, keep it non-daemon and give it a way to stop: a volatile boolean the loop checks (volatile makes every thread see the latest write), or an interrupt, a request to a thread to stop that blocking calls respond to. A thread you cannot ask to stop is a process you cannot shut down cleanly.