テキストファイルを読み取る小さな例を作成し、CompletableFuture
で呼び出しをラップしました。CompletableFutureでサプライヤを使用すると、ラムダを使用する場合とは異なる結果になる
public class Async {
public static void main(String[] args) throws Exception {
CompletableFuture<String> result = ReadFileUsingLambda(Paths.get("path/to/file"));
result.whenComplete((ok, ex) -> {
if (ex == null) {
System.out.println(ok);
} else {
ex.printStackTrace();
}
});
}
public static CompletableFuture<String> ReadFileUsingSupplier(Path file) throws Exception {
return CompletableFuture.supplyAsync(new Supplier<String>() {
@Override
public String get() {
try {
return new String(Files.readAllBytes(file));
} catch (IOException e) {
e.printStackTrace();
return "test";
}
}
}, ForkJoinPool.commonPool());
}
public static CompletableFuture<String> ReadFileUsingLambda(Path file) throws Exception {
return CompletableFuture.supplyAsync(() -> {
try {
return new String(Files.readAllBytes(file));
} catch (IOException e) {
e.printStackTrace();
return "test";
}
} , ForkJoinPool.commonPool());
}
}
このコードは何も返しません。それは実行し、 "何も起こらない"、エラーも出力もない。 ReadFileUsingLambda
の代わりにReadFileUsingSupplier
と呼ぶと、ファイルの内容がコンソールに表示されます。
ラムダはインライン関数を記述するための省略表現であり、動作を変更すべきではないが、この例では明らかにそうであるため、これは意味をなさない。
ありがとうございます。これはトリックでしたが、どのように私のプログラムがCompletableFutureから結果を返すまで終了しないようにするにはどうすればいいですか –
@SulAga単に 'result.get()'または 'result.join()'を呼び出すことができます – assylias
したがって、参加または取得はブロッキングコールですか?メインスレッドまたはCompletableFutureスレッドでブロックされていますか?これは問題です。つまりブロックします。 –