在本教程中
有两种方法可以运行内核,另一种方法在评论中提到:
1.
cl::KernelFunctor simple_add(cl::Kernel(program,"simple_add"),queue,cl::NullRange,cl::NDRange(10),cl::NullRange);
simple_add(buffer_A,buffer_B,buffer_C);
Run Code Online (Sandbox Code Playgroud)
但是,我发现,KernelFunctor 已经消失了.
所以我尝试了另一种方式:
2.
cl::Kernel kernel_add=cl::Kernel(program,"simple_add");
kernel_add.setArg(0,buffer_A);
kernel_add.setArg(1,buffer_B);
kernel_add.setArg(2,buffer_C);
queue.enqueueNDRangeKernel(kernel_add,cl::NullRange,cl::NDRange(10),cl::NullRange);
queue.finish();
Run Code Online (Sandbox Code Playgroud)
它编译和运行成功.
但是,评论中有第3个选项:
3.
cl::make_kernel simple_add(cl::Kernel(program,"simple_add"));
cl::EnqueueArgs eargs(queue,cl::NullRange,cl::NDRange(10),cl::NullRange);
simple_add(eargs, buffer_A,buffer_B,buffer_C).wait();
Run Code Online (Sandbox Code Playgroud)
哪个不编译,我认为make_kernel需要模板参数.我是OpenCl的新手,并没有设法修复代码.
我的问题是:
1.我应该如何修改3.编译代码?
2.哪种方式更好,为什么?2.对阵3.?
您可以查看OpenCL C++ 绑定规范以获取 API 的详细描述cl::make_kernel
(第 3.6.1 节),其中包括使用示例。
在您的情况下,您可以编写类似的内容来创建内核函子:
auto simple_add = cl::make_kernel<cl::Buffer&, cl::Buffer&, cl::Buffer&>(program, "simple_add");
Run Code Online (Sandbox Code Playgroud)
你的第二个问题主要是基于意见,因此很难回答。有人可能会说内核仿函数方法更简单,因为它允许您“调用”内核,就像它只是一个函数一样,并以熟悉的方式传递参数。另一种方法(问题中的选项 2)对于设置参数和将内核排队更加明确,但更接近地代表了如何使用 OpenCL C API 编写相同的代码。您使用哪种方法完全取决于个人喜好。