当前位置: 首页 > 网络知识

TBB 并行加速 parallel_for使用

时间:2026-01-26 14:19:49

一、OpenMP TBB选择

二、TBB parallel_for

2.1 构建类或者结构体

依据实际问题,构建类或者结构体,主要包含初始化和重载函数运算符注意这里重载函数运算符需要加入const限定,避免更改函数体。

1 struct MT 3 void operator() (const tbb::blocked_range<int>& r) const 4 };

2.2 调用

默认参数调用

调用tbb::parallel_for,先初始化一个类或结构体,设置并行的一个范围,可以采用如下调用方式。

1 MT mt(datas, ratio); 2 tbb::parallel_for(tbb::blocked_range<int>(0, static_cast<int>(datas.size())), mt);
控制块大小

在传入范围给tbb::parallel_for时可以控制其分块的大小,blocked_range<T>(begin,end,grainsize)grainsize默认大小为1,如果想将并行时每块大小设置为2,可以更改grainsize的大小,如下所示:

1 MT mt(datas, ratio); 2 tbb::parallel_for(tbb::blocked_range<int>(0, static_cast<int>(datas.size()), 2), mt);

如上图所示case A 和case B 具有相同的总灰色区域。case A 中粒度太小有较高的并行度,但会导致资源开销比例相对较高,case B 中相对大一点的粒度可以降低此比例,但也降低了并行度。实际使用时可以参考硬件资源和并行度对grainSize进行跳转

官网示例给出了不同grainsize对应的时间消耗。

带宽及缓存

由数据集和缓存的相对大小决定的亲和力的好处如下:

parallel_for提供了不同的方式

官网示例演示了affinity_partitionerauto_partitioner两种方式的运行时间对比。

1 MT mt(datas, ratio); 2 static tbb::affinity_partitioner ap; 3 tbb::parallel_for(tbb::blocked_range<int>(0, static_cast<int>(datas.size()), 2), mt, ap);

2.3 加锁

并行时有时会不同线程访问同一对象,避免冲突可以在相应位置加锁,然后执行完再解锁。

1 mutex_.lock(); //加锁 2 mutex_.unlock(); //解锁

2.4 完整示例

1 struct MT 4 5 void operator() (const tbb::blocked_range<int>& r) const 6 12 // mutex_.unlock(); 13 } 14 15 static tbb::mutex mutex_; 16 std::vector<double>* datas_; 17 const double ratio_; 18 }; 19 20 // tbb::mutex CpresionMT::mutex_; // global define not need init 21 22 void TestTBB(std::vector<double>& datas, double ratio, bool bMT) 23 29 MT mt(edgeOrders, datas, ratio); */ 30 tbb::mutex mutex; // if global define the not need 31 MT mt(datas, ratio, mutex); 32 static tbb::affinity_partitioner ap; 33 tbb::parallel_for(tbb::blocked_range<int>(0, static_cast<int>(datas.size()),2), mt, ap); 34 } 35 else 39 } 40 }
1 #include <chrono> 2 std::vector<double> datas1, datas2; 3 int num = 10000000; 4 for (int i = 1; i <= num; ++i) 8 double ratio = 2.0; 9 std::chrono::time_point<std::chrono::steady_clock> t1 = std::chrono::steady_clock::now(); 10 TestTBB(datas1, ratio, false); 11 std::chrono::time_point<std::chrono::steady_clock> t2 = std::chrono::steady_clock::now(); 12 std::chrono::duration<double> elapsed1 = t2 t1; 13 std::cout << "t2 t1: " << elapsed1ount() << "s\n"<< std::endl; 14 15 std::chrono::time_point<std::chrono::steady_clock> t3 = std::chrono::steady_clock::now(); 16 TestTBB(datas2, ratio, true); 17 std::chrono::time_point<std::chrono::steady_clock> t4 = std::chrono::steady_clock::now(); 18 std::chrono::duration<double> elapsed2 = t4 t3; 19 std::cout << "t4 t3: " << elapsed2ount() << "s\n" << std::endl;



上一篇:显微镜的光源
下一篇:C/C++ 三元运算符
TBB
  • 英特尔与 Vertiv 合作开发液冷 AI 处理器
  • 英特尔第五代 Xeon CPU 来了:详细信息和行业反应
  • 由于云计算放缓引发扩张担忧,甲骨文股价暴跌
  • Web开发状况报告详细介绍可组合架构的优点
  • 如何使用 PowerShell 的 Get-Date Cmdlet 创建时间戳
  • 美光在数据中心需求增长后给出了强有力的预测
  • 2027服务器市场价值将接近1960亿美元
  • 生成式人工智能的下一步是什么?
  • 分享在外部存储上安装Ubuntu的5种方法技巧
  • 全球数据中心发展的关键考虑因素
  • 英特尔与 Vertiv 合作开发液冷 AI 处理器

    英特尔第五代 Xeon CPU 来了:详细信息和行业反应

    由于云计算放缓引发扩张担忧,甲骨文股价暴跌

    Web开发状况报告详细介绍可组合架构的优点

    如何使用 PowerShell 的 Get-Date Cmdlet 创建时间戳

    美光在数据中心需求增长后给出了强有力的预测

    2027服务器市场价值将接近1960亿美元

    生成式人工智能的下一步是什么?

    分享在外部存储上安装Ubuntu的5种方法技巧

    全球数据中心发展的关键考虑因素