When using an ExecutorService
and Future
objects (when submitting Runnable
tasks), if I specify a timeout value to the future's get function, does the underlying thread get killed when a TimeoutException
is thrown?
Asked
Active
Viewed 7.3k times
68

Nico Huysamen
- 10,217
- 9
- 62
- 88
4 Answers
79
It does not. Why would it? Unless you tell it to.
There is a very valid concern here in case of a Callable for example. If you waited for the result for say 20 seconds and you did not get it, then you are not interested in the result anymore. At that time you should cancel the task at all.
Something like this:
Future<?> future = service.submit(new MyCallable());
try {
future.get(100, TimeUnit.MILLISECONDS);
} catch (Exception e){
e.printStackTrace();
future.cancel(true); //this method will stop the running underlying task
}

Eugene
- 117,005
- 15
- 201
- 306
-
37Just a comment: `future.cancel(true);` does **not** stop the running underlying task, it just sets the interrupted flag to true for the running thread. It is your code that is responsible to check this flag and throw InterruptedException if it is true. – Thiago Kronig Mar 31 '15 at 17:09
-
1@ThiagoKronig, are you sure? from the [documentation](http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/Future.html#cancel(boolean)), if you pass true, the thread should be interrupted and the attempt should fail. – Dirk Jul 27 '15 at 18:54
-
17@Dirk, from the documentation we have: _If the task has already started, then the mayInterruptIfRunning parameter determines whether the thread executing this task_ **should be interrupted in an attempt to stop the task**. _Interruption_ here means that it will set to true a volatile flag of that thread. The code running must test for this condition to be able to stop itself. The code must stop itself. – Thiago Kronig Jul 28 '15 at 14:54
-
@Thiago can you please share sample code/link on how to code inside the callable can check the flag? What exactly will the code check? – mtk Oct 14 '19 at 15:23
19
No it doesnt. Morover there is even no attempt to interrupted the task. First of all Future.get with timeout doesn't say so. Secondly, try my test to see how it behaves
ExecutorService ex = Executors.newSingleThreadExecutor();
Future<?> f = ex.submit(new Runnable() {
public void run() {
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("finished");
}
});
f.get(1, TimeUnit.SECONDS);
in 1 sec it prints
Exception in thread "main" java.util.concurrent.TimeoutException
at java.util.concurrent.FutureTask$Sync.innerGet(FutureTask.java:228)
at java.util.concurrent.FutureTask.get(FutureTask.java:91)
at Test1.main(Test1.java:23)
after another 1 sec the task successfullt finishes
finished

Evgeniy Dorofeev
- 133,369
- 30
- 199
- 275
-
1Well... that *particular* `Future` implementation doesn't. As it's an interface, one cannot make sweeping statements about all `Future`s. – Duncan Jones Apr 26 '13 at 08:11
-
7Future.get(long timeout, TimeUnit unit) doesnt say it will attempt stop the task. Besides, are there many ways to stop a running thread? – Evgeniy Dorofeev Apr 26 '13 at 08:14
-
2
5
It seems that you need to kill, cancel or shutdown the task explicitly

Community
- 1
- 1

gurvinder372
- 66,980
- 10
- 72
- 94
-1
Simply run these two lines, the program never terminates! :
Future<?> f = Executors.newSingleThreadExecutor().submit(() -> System.out.println("done"));
f.get(1, TimeUnit.SECONDS);

Atul Kumar
- 421
- 3
- 12
-
This has nothing to do with the question. The default thread factory in `SingleThreadExecutor` returns a non-daemon thread, that is why it never terminates. [Daemon Threads](https://stackoverflow.com/questions/2213340/what-is-a-daemon-thread-in-java) – Miss Chanandler Bong Jul 27 '20 at 13:48