繁体   English   中英

如何在Java中实现多核算法?

[英]How can I implement an algorithm for multicore in Java?

现代计算机具有越来越多的内核。 我们想要更改当前的线性算法以使用这些核。

仅当有空闲处理器时,将任何算法拆分为使用不同的线程才有意义。

如果有免费的处理器,是否有任何好的库可以帮助并行化某些步骤?

我会举一些例子。

  • 如果只有一个处理器,则创建多个线程是没有意义的。 它将降低速度。
  • 如果在核心二人组上运行2个进程(服务器上的请求),则启动线程也没有意义。
  • 如果一个核心二人组上只有一个进程,那是有道理的。

抽象算法具有4个步骤A,B,C和D。步骤A,B和C可以并行执行。 步骤D需要A,B和C的结果。

编辑:我的意思是一种数学算法。 没有IO,没有事件等

这不一定是真的。

根据算法的不同,即使只有一个内核可用,将其拆分为多个线程也很有意义。 如果套接字,IO等上有任何等待,您可以从中受益。 如果有2个进程,则“其他”进程可能未使用100%的其他内核,因此线程在这里可以提供帮助。 在这种情况下,请信任您的操作系统以正确处理它。

您始终可以使用Runtime.availableProcessors()检查处理器数量,以确定如何将其拆分为单独的线程。 或者,您可以使用线程池,该线程池应在更多处理器上正确扩展。

不过,总的来说,如果可以并行化,我会设计您的算法使用多个处理器。 大多数系统将具有更多可用的内核/处理器,如果以后发现需要,可以随时对实现进行调整。 如果该进程运行时间长,那么生成线程的开销将是值得的;如果它已经很快,那么寻找其他地方进行优化可能更值得。

查看Java 5及更高版本中的各种并发类。 您最可能希望使用ThreadPoolExecutor- http://java.sun.com/javase/6/docs/api/java/util/concurrent/ThreadPoolExecutor.html

ThreadPool的适当值很可能会因工作负载和硬件体系结构而异,因系统而异。 使其用户可调。

抽象算法具有4个步骤A,B,C和D。步骤A,B和C可以并行执行。 步骤D需要A,B和C的结果。

这是使用Ateji PX表示法(Java语言的扩展)的单行代码:

[ A(); || B(); || C(); ]; D();

您作为程序员的责任是表达在哪里有可能执行并行,这就是平行杠“ ||”的作用。 在代码中。 现在,调度程序可以充分利用可用的硬件,即在可用时在三个不同的内核上运行A,B和C。

这是一个非常高级的视图,可能在A,B或C内部表现出更多的并行性。

对于某些想法,请看一下JSR166和JSR166y (类似于带有工作窃取功能(166)和并行阵列(166y)的fork-join系统)。

对Java的未来方向有一些不错的阅读和概述。 看起来还不错(强烈支持高级并发和并行编程)。

我经常有一个固定的线程池,该线程池的线程数与处理器的数量动态相同(请参阅运行时),我向该线程池添加任务,以便它使用所有可用的处理器。

我不认为您应该尝试在操作系统中重新发明流程调度程序。 它做得很好,所以就让它做好它。

具有比核心更多的线程/进程不一定是一件坏事。 如果您的代码严格来说是数学的,且I / O很少且没有副作用,那么可以,内核与线程之间的1:1对应关系是最佳选择。 但这通常不是这种情况。 与时钟周期相比,I / O花费了无数的时间。 当操作系统可以交换另一个线程以保持同步时,为什么在等待I / O时完全停滞内核呢?

问题在于,没有多少语言/编译器会为您做出并发决策。 您需要设计程序以利用并发性。 您可能需要针对多个目标环境设计程序,通常情况下不受您的控制。 因此,通常,最佳实践是使线程并行处理,并由线程调度程序处理。 应该调整线程调度程序以在有问题的特定硬件上使用,比为“随随便便的硬件”调整程序要好得多。

我认为您需要来自Javolution的ConcurrentContext。 参见http://javolution.org/target/site/apidocs/javolution/context/ConcurrentContext.html

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM