java - 如何为所有 CompletableFuture 全局设置线程池

标签 java

我试图使用 EA 的 async/await 库来模仿 Java 中 Javascript 的单线程异步编程( ea-async )。这主要是因为我的程序中没有持久的 CPU 密集计算,并且我想用 Java 编写单线程无锁代码。

ea-async 库严重依赖于 Java 中的 CompletableFuture,并且在 Java 底层似乎使用 ForkJoinPool 来运行异步回调。这使我进入多线程环境,因为我的 CPU 是多核的。似乎对于每个 CompletableFuture 任务,我都可以使用我的自定义线程池执行器提供异步。我可以供应Executors.newSingleThreadExecutor()为此,但我需要一种全局设置的方法,以便所有 CompletableFuture 都将在单个 JVM 进程中使用此执行器。我该怎么做?

最佳答案

ea-async library heavily relies on the CompletableFuture in Java and underneath Java seems to use ForkJoinPool to run the async callbacks.

这是 CompleteableFuture 的默认行为:

All async methods without an explicit Executor argument are performed using the ForkJoinPool.commonPool() (unless it does not support a parallelism level of at least two, in which case, a new Thread is created to run each task). This may be overridden for non-static methods in subclasses by defining method defaultExecutor().

这是该类的定义特征,因此,如果您使用类 CompleteableFuture,而不是子类,并且在未显式指定 Executor 的情况下生成实例,那么您将获得 ForkJoinPool

当然,如果您可以控制提供给 ea-async 的 CompletableFuture,那么您可以选择提供定义 defaultExecutor() 的子类实例,无论您喜欢什么。或者,您可以通过静态工厂方法创建 CompleteableFuture 对象,这些方法允许您显式指定要使用的 Executor,例如 runAsync​(Runnable, Executor) .

但这可能不是您真正想做的

如果您使用只有一个线程的执行器,那么您的任务可以相对于提交它们的线程异步执行,是的,但它们将相对于彼此进行序列化。您确实只有一个线程在处理它们,但它会随时处理特定的线程,只坚持该线程直到完成,无论响应实际到达的顺序如何。如果这令人满意,那么就不清楚为什么需要异步操作。

This puts me into multi threaded environment as my CPU is multi-core.

无论您的 CPU 有多少个核心,它都会让您处于多个线程中。这就是 Executor 的作用,甚至是 Executors.newSingleThreadExecutor() 的作用。这就是它们提供的“异步”的意义。

如果我理解正确的话,您会希望使用一个线程将 I/O 复用到多个远程 Web 应用程序。这就是 java.nio.channels.Selector 的用途,但使用它通常需要您自己管理 I/O 操作或使用旨在与选择器互操作的接口(interface)。如果您被锁定到无法使用选择器的第三方接口(interface),那么多线程和多处理是您唯一可行的选择。

在您写的评论中:

I'm starting to think maybe BlockingQueue might do the job in consolidating all API responses into one queue as tasks where a single thread will work on them.

再说一遍,我不认为您想要随之而来的一切,如果您确实想要,那么我不明白为什么同步工作不是比异步工作更好、更容易。

关于java - 如何为所有 CompletableFuture 全局设置线程池,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55911218/

相关文章:

java - 设计随机生成的简单(不相交)曲线

Java-创建一个 String 对象但之后分配

Java - 比较

java - 如何从Android中的SD卡中删除捕获的视频

java - 复合模式实现

java - 框架未设置为 Java 定义的大小

java - 在 Linux 服务器 Java 中创建一个文件

Java 反射性能问题

java - 从 child 更新父类 UI

java - 自动查找和裁剪相关图像区域