在这个链接std::function vs template中有一个很好的讨论关于 std::function 的开销。基本上,为了避免传递给 std::function 构造函数的函子堆分配导致的 10 倍开销,必须使用 std::ref 或 std::cref。
取自@CassioNeri 答案的示例,该示例显示了如何通过引用将 lambda 传递给 std::function。
float foo(std::function<float(float)> f) { return -1.0f * f(3.3f) + 666.0f; }
foo(std::cref([a,b,c](float arg){ return arg * 0.5f; }));
现在,英特尔线程构建模块库使您能够使用 lambda/functor 并行评估循环,如下例所示。
示例代码:
#include "tbb/task_scheduler_init.h"
#include "tbb/blocked_range.h"
#include "tbb/parallel_for.h"
#include "tbb/tbb_thread.h"
#include <vector>
int main() {
tbb::task_scheduler_init init(tbb::tbb_thread::hardware_concurrency());
std::vector<double> a(1000);
std::vector<double> c(1000);
std::vector<double> b(1000);
std::fill(b.begin(), b.end(), 1);
std::fill(c.begin(), c.end(), 1);
auto f = [&](const tbb::blocked_range<size_t>& r) {
for(size_t j=r.begin(); j!=r.end(); ++j) a[j] = b[j] + c[j];
};
tbb::parallel_for(tbb::blocked_range<size_t>(0, 1000), f);
return 0;
}
所以我的问题是:英特尔 TBB parallel_for 是否具有与我们在 std::function 上看到的相同类型的开销(函子的堆分配)?我是否应该使用 std::cref 通过引用 parallel_for 来传递我的仿函数/lambdas 来加速代码?