java.util.concurrent.Future.get() not returning
Solution 1
As in Executor.execute() Javadoc:
Executes the given command at some time in the future. The command may execute in a new thread, in a pooled thread, or in the calling thread, at the discretion of the Executor implementation.
So, the method execute()
returns immediately leaving you with no option to query to status of submitted task.
On the other hand ExecutorService.submit():
Submits a Runnable task for execution and returns a Future representing that task. The Future's get method will return null upon successful completion.
The Future.get() will return only after successful competion, so never in your case.
This is further noted in Future.get() documentation:
Waits if necessary for the computation to complete, and then retrieves its result.
Solution 2
I created an SSCCE:
package com.stackoverflow.q2585971;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
public class Test {
public static void main(String args[]) throws Exception {
ExecutorService executor = Executors.newCachedThreadPool();
Future<?> future = executor.submit(
new Runnable() {
public void run() {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
System.out.println("Epic fail.");
}
}
}
);
System.out.println("Waiting for task to finish..");
future.get();
System.out.println("Task finished!");
executor.shutdown();
}
}
It works perfectly fine. It first prints
Waiting for task to finish..
then after one second you see
Task finished!
So, your problem lies somewhere else. I'll duplicate my comment on your question here:
Your question is pretty confusing. The first construct should just work. The confusion is in "returning". Don't you just mean "finishing" or "executing"? Your confusion seems to be based on the fact that
future.get()
actually waits for the runnable to be finished and thus will block the thread and prevent it from executing the remnant of the code after thefuture.get()
line.
Solution 3
Java futures are blocking! get(). This method blocks the current thread until a future instance completes its work, thus requiring the use of one thread more than the work that must be performed just to manage what happens when it is done
JanusFox81
I am interested in functional programming. I am also interested in music programming, such as in ChucK or impromptu. My favorite language is Lisp.
Updated on July 09, 2022Comments
-
JanusFox81 almost 2 years
I have the following Java code:
final Future future = exeService.submit( new Runnable() { public void run() { myObject.doSomething(); } } ); future.get();
where
exeService
is an instance ofjava.util.concurrent.ExecutorService
The problem is that
myObject.doSomething()
never returns, and, hence,future.get()
never returns.However, if I replace the call to
submit
with a call toexecute
like this:exeService.execute( new Runnable() { public void run() { myObject.doSomething(); } } );
the call to
myObject.doSomething()
does return. I don't know if it matters, butdoSomething()
is avoid
method.Why is
doSomething()
finishing when usingexecute
but not when usingsubmit
?Also, I don't need to use
Future.get()
; that just seemed to be the most natural way of doing this. (I also run into the same problem withCountdownLatch
.) The point is that I need to wait fordoSomething()
to finish before proceeding, and, for complicated reasons I won't go into here, I need to launch it on a separate thread. If there is another way of doing this that works, that would be fine.