在 CompletableFuture 中等待 CompletableFutures?
Await CompletableFutures inside a CompletableFuture?
我正在尝试执行等待多个其他异步操作的异步操作。我该如何使用 CompletableFutures 执行此操作?
这是我想在不调用 join 的情况下实现的,我实际上希望那些触发的操作 运行 彼此异步。
myDatabaseOperation.thenApplyAsync(){
for(var i = 0; i < 3; i++) triggerOtherAsyncOperations();
// Await triggered operations...
return calculatedValueFromOperations;
}
这是我到目前为止得到的。问题是 CompletableFuture.allOf()
没有按预期工作。它只是不阻止异步操作并继续,这打破了未来。
var queryTask = database.getAsync("select i from Identity i where i.id in "+list.toString(), Identity.class);
var loadComponentsTask = queryTask.thenApplyAsync(identities -> {
var loadingTasks = new HashSet<CompletableFuture<Set<Integer>>>();
var typeIDs = HibernateComponentUtils.mergeByComponents(identities, prototypeHierachy::get);
// Start all loading tasks
for(var entry : typeIDs.entrySet()){
var sqlList = HibernateQueryUtils.toSQLList(entry.getValue());
var loadingTask = loadEntitiesAsync(entry.getKey(), " where identity.id in "+sqlList);
loadingTasks.add(loadingTask);
}
// Await all started loading tasks without blocking the mainthread
var loadingTasksArray = loadingTasks.toArray(CompletableFuture[]::new);
CompletableFuture.allOf(loadingTasksArray);
// Add all loaded entities from each task to a set
var loadedEntities = new HashSet<Integer>();
for(var task : loadingTasks) loadedEntities.addAll(task.join());
return (Set<Integer>)loadedEntities;
});
return loadComponentsTask;
我做错了吗?我错过了什么?在异步操作中等待异步操作的正确方法是什么?
CompletableFuture.allOf(...)
不应该阻止。它 returns 一个 CompletableFuture 如果你想等待你可以调用 join/get.
CompletableFuture.allOf(...).join();
但这不是最好的解决方案。
我认为更好的解决方案是:
var loadComponentsTask = queryTask.thenComposeAsync(identities -> {
...
return CompletableFuture.allOf(loadingTasksArray)
.thenApply( v -> {
// Add all loaded entities from each task to a set
var loadedEntities = new HashSet<Integer>();
for(var task : loadingTasks) {
loadedEntities.addAll(task.join());
}
return (Set<Integer>) loadedEntities;
});
});
我正在尝试执行等待多个其他异步操作的异步操作。我该如何使用 CompletableFutures 执行此操作?
这是我想在不调用 join 的情况下实现的,我实际上希望那些触发的操作 运行 彼此异步。
myDatabaseOperation.thenApplyAsync(){
for(var i = 0; i < 3; i++) triggerOtherAsyncOperations();
// Await triggered operations...
return calculatedValueFromOperations;
}
这是我到目前为止得到的。问题是 CompletableFuture.allOf()
没有按预期工作。它只是不阻止异步操作并继续,这打破了未来。
var queryTask = database.getAsync("select i from Identity i where i.id in "+list.toString(), Identity.class);
var loadComponentsTask = queryTask.thenApplyAsync(identities -> {
var loadingTasks = new HashSet<CompletableFuture<Set<Integer>>>();
var typeIDs = HibernateComponentUtils.mergeByComponents(identities, prototypeHierachy::get);
// Start all loading tasks
for(var entry : typeIDs.entrySet()){
var sqlList = HibernateQueryUtils.toSQLList(entry.getValue());
var loadingTask = loadEntitiesAsync(entry.getKey(), " where identity.id in "+sqlList);
loadingTasks.add(loadingTask);
}
// Await all started loading tasks without blocking the mainthread
var loadingTasksArray = loadingTasks.toArray(CompletableFuture[]::new);
CompletableFuture.allOf(loadingTasksArray);
// Add all loaded entities from each task to a set
var loadedEntities = new HashSet<Integer>();
for(var task : loadingTasks) loadedEntities.addAll(task.join());
return (Set<Integer>)loadedEntities;
});
return loadComponentsTask;
我做错了吗?我错过了什么?在异步操作中等待异步操作的正确方法是什么?
CompletableFuture.allOf(...)
不应该阻止。它 returns 一个 CompletableFuture 如果你想等待你可以调用 join/get.
CompletableFuture.allOf(...).join();
但这不是最好的解决方案。
我认为更好的解决方案是:
var loadComponentsTask = queryTask.thenComposeAsync(identities -> {
...
return CompletableFuture.allOf(loadingTasksArray)
.thenApply( v -> {
// Add all loaded entities from each task to a set
var loadedEntities = new HashSet<Integer>();
for(var task : loadingTasks) {
loadedEntities.addAll(task.join());
}
return (Set<Integer>) loadedEntities;
});
});