制作内核的不同方法

oti*_*oza 13 c++ opencl

在本教程中

有两种方法可以运行内核,另一种方法在评论中提到:

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.?

jpr*_*ice 4

您可以查看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 编写相同的代码。您使用哪种方法完全取决于个人喜好。