gpt4 book ai didi

java - CompletableFuture 供应异步有时在主线程上运行

转载 作者:行者123 更新时间:2023-11-30 06:10:11 28 4
gpt4 key购买 nike

我一直在尝试 Java 8 CompletableFutures。据我了解,调用 CompletableFuture.supplyAsync(Supplier seller, Executor executor) 总是会在传入的 Executor 提供的线程中运行作业,但我注意到,当我传递给供应商时,它有时会在主线程上运行这是相当“简单”的。我的测试代码是:

import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.atomic.AtomicInteger;

public class SyncTest {

public static void main(String[] args) {
ExecutorService pool = Executors.newFixedThreadPool(5);

CompletableFuture<?>[] cfs = new CompletableFuture<?>[10];
AtomicInteger mainCount = new AtomicInteger();
for (int i = 0; i < cfs.length; i++) {
int index = i;
CompletableFuture<Integer> cf =
CompletableFuture.supplyAsync(() -> {
return index;
}, pool).thenApply(j -> {
if (Thread.currentThread().getName().equals("main")) {
mainCount.incrementAndGet();
}

System.out.println(Thread.currentThread().getName() + ": " + index + ": doing a heavy computation");
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
return j;
});
cfs[i] = cf;
}

System.out.println(Thread.currentThread().getName() + " doing other stuff");
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}

CompletableFuture.allOf(cfs).join();
pool.shutdown();
System.out.println("Jobs on main: " + mainCount.get());
}
}

我得到的输出是这样的:

main: 0: doing a heavy computation
main: 1: doing a heavy computation
pool-1-thread-3: 2: doing a heavy computation
pool-1-thread-4: 3: doing a heavy computation
main: 4: doing a heavy computation
main doing other stuff
pool-1-thread-4: 9: doing a heavy computation
pool-1-thread-5: 8: doing a heavy computation
pool-1-thread-2: 7: doing a heavy computation
pool-1-thread-1: 6: doing a heavy computation
pool-1-thread-3: 5: doing a heavy computation
Jobs on main: 3

我知道这是一个相当简单的示例,并且 CompletableFutures 还有其他方法(例如 thenSupplyAsync 和completedFuture)可以使用它们,我更好奇其中一些任务如何可能在主线程上执行线程。

最佳答案

打印“doing a HeavyComputation”的任务是用thenApply调用的,这意味着您没有指定执行器来运行该任务,系统可以自由使用任何执行器,包括当前线程。

如果您希望此作业在预定义执行器上执行,请改用 thenApplyAsync,带或不带第二个参数 - 执行器。

关于java - CompletableFuture 供应异步有时在主线程上运行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50418870/

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