VecCL、Thrust和Boost.Computer之间的差异
Differences between VexCL, Thrust, and Boost.Compute
只要粗略了解一下这些库,它们看起来就非常相似。我知道VexCL和Boost.Compute使用OpenCl作为后端(尽管v1.0版本的VexCL也支持CUDA作为后端),Thrust使用CUDA。除了不同的后端,它们之间有什么区别。
具体来说,它们解决了什么问题空间,以及我为什么要使用其中一个而不是另一个。
此外,在推力常见问题解答中,
OpenCL支持的主要障碍是缺乏支持C++模板的OpenCL编译器和运行时
如果是这样的话,那么VexCL和Boost.Computer怎么可能存在呢。
我是VexCL的开发者,但我真的很喜欢Boost.Computer的作者Kyle Lutz在Boost邮件列表上对同一主题所说的话。简言之,从用户的角度来看,Thrust、Boost.Computer、AMD的Bolt以及可能是微软的C++AMP都实现了类似STL的API,而VexCL是一个基于表达式模板的库,本质上更接近于Eigen。我相信类似STL的库之间的主要区别在于它们的可移植性:
- Thrust只支持NVIDIA GPU,但也可以通过其OpenMP和TBB后端在CPU上工作
- Bolt使用AMD对OpenCL的扩展,这些扩展仅在AMD GPU上可用。它还提供Microsoft C++AMP和Intel TBB后端
- 唯一支持Microsoft C++AMP的编译器是Microsoft Visual C++(尽管将C++AMP引入Windows之外的工作正在进行中)
- Compute似乎是其中最便携的解决方案,因为它基于标准的OpenCL
同样,所有这些库都试图实现类似STL的接口,因此它们具有非常广泛的适用性。VexCL的开发考虑到了科学计算。如果Boost.Computer开发得更早一点,我可能会将VexCL建立在它之上:)。另一个值得一看的科学计算库是ViennaCL,这是一个免费的开源线性代数库,用于在许多核心架构(GPU、MIC)和多核CPU上进行计算。请参阅[1],以比较该领域的VexCL、ViennaCL、CMTL4和Thrust。
关于Thrust开发人员无法添加OpenCL后端的问题:Thrust、VecCL和Boost.Computer(我不熟悉其他库的内部结构)都使用元编程技术来完成它们的工作。但由于CUDA支持C++模板,Thrust开发人员的工作可能更容易一些:他们必须编写元程序,在C++编译器的帮助下生成CUDA程序。VecCL和Boost.Computer作者编写元程序,生成生成OpenCL源代码的程序。请看一下我试图解释如何实现VexCL的幻灯片。所以我同意目前Thrust的设计禁止他们添加OpenCL后端。
[1] Denis Demidov,Karsten Ahnert,Karl Rupp,Peter Gottschling,编程CUDA和OpenCL:使用现代C++库的案例研究,SIAM J.Sci。计算。,35(5),C453–C472。(也提供arXiv版本)。
更新:@gnzlbg评论说,在基于OpenCL的库中不支持C++函数和lambdas。事实上,OpenCL是基于C99的,并且是从运行时存储在字符串中的源代码编译的,因此没有简单的方法可以与C++类完全交互。但公平地说,基于OpenCL的库确实支持基于用户的函数,甚至在某种程度上支持lambda。
- Boost.Compute提供了自己的简单Lambda实现(基于Boost.Proto),并允许通过Boost_Compute_DAPT_STRUCT和Boost_MPUTE_CLOSURE宏与用户定义的结构进行交互
- VecCL提供了类似DSL的线性代数(也基于Boost.Proto),还支持将通用C++算法和函数(甚至Boost.Fenix lambdas)转换为OpenCL函数(有限制)
- 我相信AMD的Bolt确实通过其C++for OpenCL扩展魔法支持用户定义的函数
话虽如此,基于CUDA的库(可能是C++AMP)与实际编译时编译器相比具有明显的优势(你能这么说吗?),因此与用户代码的集成可能会更加紧密。
- C++中std::resize(n)和std::shrink_to_fit之间的区别
- int(c) 和 c-'0' 之间的区别。C++
- 在cuda线程之间共享大量常量数据
- 在c代码之间共享数据的最佳方式
- Mix_Init和Mix_OpenAudio SDL之间的区别是什么
- C++ 使用 assign 函数的字符串与直接使用 '=' 更改值的字符串之间的区别
- VSOMEIP-2个设备之间的通信(TCP/UDP)不工作
- std::atomic和std::condition_variable wait,notify_*方法之间的区别
- 大小相等但成员数量不同的结构之间的性能差异
- 类与私有变量的其他类之间的线程安全性
- 如何在cpp文件之间切换窗口?在Qt中
- 线程之间的布尔停止信号
- 我是C++编程的新手,这些代码之间有什么区别,我应该使用哪一个
- 在 const 函数中通过引用和指针返回之间的区别
- 我想知道长双倍和双倍之间的区别
- 如何防止clang格式在流运算符调用之间添加换行符<<
- 在两台机器之间进行时间戳的最佳c++chrono函数是什么
- 使用.find函数在c++中查找字符和另一个字符之间的大小
- 构造函数和转换运算符之间的重载解析
- VecCL、Thrust和Boost.Computer之间的差异