并发与并行 - 特别是在 C++ [关闭]

Posted

技术标签:

【中文标题】并发与并行 - 特别是在 C++ [关闭]【英文标题】:Concurrency vs Parallelism - Specifically in C++ [closed] 【发布时间】:2016-09-11 15:02:37 【问题描述】:

我了解两者之间的基本区别,我经常在我的程序中使用 std::async,这给了我并发性。

是否有任何可靠/值得注意的库可以在 C++ 中提供并行性? (我知道这可能是 C++17 的一个特性)。如果有,您对他们有什么体验?

谢谢! 芭芭拉

【问题讨论】:

<algorithm> 库现在有很多并行版本,但这些是否提供有意义的优势取决于您选择的实现。 @KerrekSB 哪个编译器实际实现了算法的并行版本? 【参考方案1】:

Threading Building Blocks (TBB) 是一个用于任务并行的模板化 C++ 库。该库包含专门用于任务并行性的各种算法和数据结构。我已经成功地使用了 parallel_for 和 parallel_pipeline 来大大加快计算速度。通过一些额外的编码,TBB 的 parallel_for 可以采用适合并行执行的串行 for 循环并使其执行(参见示例 here)。 TBB 的 parallel_pipeline 能够执行一系列相关任务,并且可以选择并行或串行执行每个任务(参见示例 here)。网络上有更多示例,尤其是 software.intel.com 和 *** (see here)。

OpenMP 是一种主要通过编译器指令访问的线程并行 API。虽然,我更喜欢使用 TBB 提供的更丰富的功能集,但 OpenMP 可以是测试并行算法和代码的一种快速方法(只需添加一个 pragma 并设置一些构建设置)。一旦事情经过测试和试验,我发现将 OpenMP 的某些用途转换为 TBB 可以相当容易地完成。这并不是说 OpenMP 不适用于严肃的编码。事实上,在某些情况下,人们可能更喜欢 OpenMP 而不是 TBB(一种是因为它主要依赖于 pragma,所以切换到串行执行比使用 TBB 更容易。)。在discussion 中可以找到许多使用 OpenMP 的开源项目。网上有很多关于 OpenMP 的示例(例如,on wikipedia)和教程,包括关于 *** 的许多问题。

我之前忽略了关于SIMD(单指令,多数据)的讨论,它提供了数据并行性。正如下面的 cmets 中所指出的,OpenMP 是探索 SIMD 的一个选项(请查看 link)。诸如SSE 和AVX(都是x86 指令集架构的扩展)以及NEON(ARM 架构)等指令集的扩展也值得探索。我在使用 SSE 和 AVX 方面有好有坏的经验。好处是它们可以为某些算法提供很好的加速(特别是我使用了Intel intrinsics)。不好的是,使用这些指令的能力取决于特定的 CPU 支持,这可能会导致意外的运行时异常。

特别是在并行性和数学方面,我在使用Intel MKL(现在有一个no cost option)和OpenBLAS 方面有很好的经验。这些库提供常见数学函数/例程的优化、并行和/或矢量化实现(例如,BLAS 和LAPACK)。还有更多可用的库专门处理数学,这些库在某种程度上涉及优化的并行性。虽然它们可能无法提供较低级别的并行构建块(例如,操作线程、调度任务的能力),但利用(并贡献于)计算数学领域的大量研究和工作是非常值得的。对于数学以外的感兴趣的领域,可以说类似的声明。

【讨论】:

OpenMP 不仅仅是测试并行算法的玩具。另外,我认为有必要指出 TBB 基于任务并行,而 OpenMP 基于线程并行(它也具有 SIMD 功能,但主要用于线程并行)。 @Zboson,我更新了我的答案以反映对 OpenMP 的更中立的立场,并纳入您的评论。除了我对 TBB 的偏好之外,OpenMP 是一个非常有价值的工具。我间接地将它用作 OpenCV 和英特尔 MKL 的一部分。我不知道 OpenMP 的 SIMD 功能。我添加了一个关于 SIMD 的简短段落,因为它与数据并行性有关。

以上是关于并发与并行 - 特别是在 C++ [关闭]的主要内容,如果未能解决你的问题,请参考以下文章

01-并行与并发

C/C++ 并行搜索 算法

C/C++ 并行搜索 算法

并发编程基础概念

使用 GUID 作为主键的最佳做法是啥,特别是在性能方面? [关闭]

C++11 并发编程基础:并发并行与C++多线程