gpt4 book ai didi

java - @Async 阻止线程继续,直到其他线程完成

转载 作者:IT老高 更新时间:2023-10-28 13:47:51 26 4
gpt4 key购买 nike

我有一个应用程序需要计算一定次数的东西。此计算函数具有注释 @Async(来自 Spring 框架),这使得可以在 4 个线程上运行这些计算。问题是我需要大约 40000 个这样的计算,我想知道所有计算的开始和结束之间的时间,所以我看到调用计算函数的 for 循环之前和之后的时间。但是现在所有的计算都放在一个队列中,所以 for 循环立即结束,时间大约是 1 秒,而计算需要几个小时才能完成。我尝试将最大队列大小设置为大约 100(也有助于减少内存使用)但这也不是解决方案,因为我会错过总时间的最后 100 次计算。有没有办法在 for 循环之后暂停执行代码,直到所有线程完成工作,但仍然能够使用 @Async 注释?

这是一些说明相同问题的代码:

执行类:

public class Foo {
public void executeBlaALotOfTimes() {
long before = System.currentTimeMillis();

for (int i = 0; i<40000; i++) {
executeBla();
}

long after = System.currentTimeMillis();

System.out.println("Time it took for a lot of bla to execute: " + (after - before) / 1000.0 + " seconds.");
}
}

以及执行计算的类:

@Service
public class Bar {
@Async
public void executeBla() {
System.out.println("Bla!");
}
}

这将导致以下输出(假设 Foo 中的代码执行得无限快):

Time it took for a lot of bla to execute: 0.0 seconds.Bla!Bla!Bla!Bla!...etc

最佳答案

如果您需要等待执行完成,那么您可以返回一个 Future 作为返回值,例如

@Async
public Future<Void> executeBla() {
System.out.println("Bla!");
return new AsyncResult<Void>(null);
}

这有点人为,因为没有返回实际值,但它仍然允许调用代码等待所有执行完成:

public void executeBlaALotOfTimes() {
long before = System.currentTimeMillis();

Collection<Future<Void>> futures = new ArrayList<Future<Void>>();

for (int i = 0; i<40000; i++) {
futures.add(executeBla());
}

for (Future<Void> future : futures) {
future.get();
}

long after = System.currentTimeMillis();

System.out.println("Time it took for a lot of bla to execute: " + (after - before) / 1000.0 + " seconds.");
}

在这里,第一个循环触发异步任务并将 future 存储在列表中。秒循环然后迭代 future ,等待每个完成。

关于java - @Async 阻止线程继续,直到其他线程完成,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4324212/

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