This is what I typically use to convert a sync method to a background Future. The benefit is that it avoids a lot of custom code (creating threads, locks, etc ) and seems simple enough, and it's relatively easy to cut&paste.
Original:
New code:
Original:
Result1 slowMethod1(Param1 p1, Param2 p2) throws Exception1 {
}
Result2 slowMethod2() throws Exception2 {
}
void caller() throws Exception1, Exception2 {
// slowMethod1 and slowMethod2 are independent of each other
Result1 r1 = slowMethod1(p1, p2); // first expensive operation
Result2 r2 = slowMethod2(); // other slow method, not using the result or side-effects of the first
}
New code:
Executor bgTasks = Executors.newCachedThreadPool();
FutureslowMethod1Future(final Param1 p1, Param2 p2) {
FutureTaskfr = new FutureTask (new Callable () {
public Result1 call() {
return slowMethod1(p1, p2);
}
});
bgTasks.execute(fr);
return fr;
}
void caller() {
Futurefr = slowMethod1Future(p1, p2);
Result2 r2 = slowMethod2();
try {
Result1 r1 = fr.get();
} catch(InterruptedException e) {
throw new RuntimeException(...);
} catch (ExecutionException e) {
Throwable t = e.getCause();
if (t intanceof Exception1) {
throw (Exception1) t;
} else {
throw new RuntimeException(t);
}
}
}