関数からの戻り値が必要かどうかは述べていませんが、データベースにアクセスするという事実を考えると、その可能性は非常に高いようです。これに対する非常に優れた簡単な解決策は、Executor と Future を使用することです。
完全なコード例は次のとおりです。
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
public class FuturesExample {
public interface ReturnTypeOne {}
public interface ReturnTypeTwo {}
public void runTwo() {
ExecutorService executor = Executors.newFixedThreadPool(2);
// Dispatch two tasks.
Future<ReturnTypeOne> first = executor.submit(new Callable<ReturnTypeOne>() {
@Override
public ReturnTypeOne call() throws Exception {
// Work, work, work...
return null;
}
});
Future<ReturnTypeTwo> second = executor.submit(new Callable<ReturnTypeTwo>() {
@Override
public ReturnTypeTwo call() throws Exception {
// Work, work, work...
return null;
}
});
// Get the results.
try {
ReturnTypeOne firstValue = first.get();
ReturnTypeTwo secondValue = second.get();
// Combine the results.
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
}
これは 2 つのセクションで構成されています。最初に、2 つのタスクがスレッド プールに送信されます。各 ExecutorService.submit() 呼び出しは、タスク計算の将来の値をすぐに返します。タスクは submit() 呼び出しですぐにディスパッチされ、バックグラウンドで実行されます。もちろん、2 つ以上のタスクをディスパッチすることもできます。
2 番目のセクションでは、先物の値が取得されます。Future.get() の呼び出しは、値が計算されるまで現在のスレッドをブロックします。いずれかのタスクがブロックされているわけではありません。それらはすべて実行されており、スレッドは特定のタスクが完了して値を返すまで待機します。最初の値が返されると、2 番目の Future.get() 呼び出しが行われます。この場合、ブロックする場合とブロックしない場合があります。2 番目のタスクが既に (おそらく最初のタスクの前に) 終了している場合、値はすぐに返されます。2 番目のタスクがまだ実行中の場合、呼び出しは値が計算されるまで現在のスレッドをブロックします。
上記の要約は、メインスレッドが最も長く実行されているタスクの間だけ待機するということです。必要なものだけ。