gpt4 book ai didi

java - CompletableFuture join() 方法出现巨大延迟

转载 作者:太空宇宙 更新时间:2023-11-04 09:06:04 27 4
gpt4 key购买 nike

所以我正在开发一个必须同时进行 20 多个 HTTP 调用的应用程序。他们每个人都需要 2-3 秒才能得到回应。一次进行一个调用非常慢(最多 40 秒),因此我尝试通过 CompletableFutures 异步发送它们。这应该允许我在等待其他人的响应时调用电话,理论上将总时间减少到 4-5 秒而不是 40 秒。

我做了一个与本教程非常相似的设置,我在https://www.codepedia.org/ama/how-to-make-parallel-calls-in-java-with-completablefuture-example找到了这个教程。 .

import org.codingpedia.example;

import javax.inject.Inject;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.function.Supplier;
import java.util.stream.Collectors;

public class ParallelCallsDemoService {

@Inject
RestApiClient restApiClient;

private ExecutorService es = Executors.newFixedThreadPool(20);

public List<ToDo> getToDos(List<String> ids){

List<CompletableFuture<ToDo>> futures =
ids.stream()
.map(id -> getToDoAsync(id))
.collect(Collectors.toList());

List<ToDo> result =
futures.stream()
.map(CompletableFuture::join)
.collect(Collectors.toList());

return result;
}


CompletableFuture<ToDo> getToDoAsync(String id){

CompletableFuture<ToDo> future = CompletableFuture.supplyAsync(() -> {
return restApiClient.makeSomeHttpCall(id);
}, es);

return future;
}

}

从所有方面来看,它似乎都在工作 - 调用几乎在同一时间发送,并且它们都在几秒钟内返回。但随后我在这部分遇到了 30-40 秒的巨大延迟:

        List<ToDo> result =
futures.stream()
.map(CompletableFuture::join)
.collect(Collectors.toList());

这使得它花费的时间与串行发送的时间大致相同,这让我感到困惑。为什么我在几秒钟内就收到了所有回复,但在加入这些回复时却出现了 30 秒的延迟?几乎就像(尽管表面上)它们仍在连续制作。为什么加入需要这么长时间?

最佳答案

终于明白了!感谢大家的建议。事实证明,这与我的 CompletableFutures 实现无关。当我收到来自服务的响应时,我使用 JAXB 将 java 对象转换为 XML 字符串以用于日志记录。当线程挂起时,我开始查看线程转储,并意识到线程实际上正在等待 JAXB 字符串转换(响应对象非常大)。我把那部分拿出来,性能立即提高到了应有的水平。

关于java - CompletableFuture join() 方法出现巨大延迟,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60213646/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com