线程构建块的任务

时间:2010-08-03 13:11:22

标签: c++ tbb

以下是示例代码:

#include <iostream>
#include <list>
#include <tbb/task.h>
#include <tbb/task_group.h>
#include <stdlib.h>
#include <boost/thread.hpp>

using namespace tbb;

 long fib(long a)
{
  if (a < 2) return 1;

  return fib(a - 1) + fib(a - 2);
}

class PrintTask 
{
public:
    void operator()()
    {
        std::cout << "hi world!: " <<  boost::this_thread::get_id() << std::endl;

        fib(50);
    }
};

int main(int argc, char** argv)
{     
    task_group group;

    for (int i = 0; i < 100; ++i)
    {
      group.run(PrintTask());
    }      

    group.wait();

    return(0);
}

这里我正在计算一个大的斐波那契序列,只是为了模拟非阻塞计算。我说这个代码会生成两个以上的线程(我的计算机是Core2Duo),但只调用第一个和第二个任务。这是指定的?

2 个答案:

答案 0 :(得分:3)

是的,这是预期的行为。

TBB是一个用于并行化PERFORMANCE代码的库。它不是为异步任务设计的 - 官方文档声明你应该使用另一个库,例如pthreads来完成这些任务(或者你的情况下使用boost :: thread)。

为了获得最佳性能,拥有比核心更多的线程没有任何意义,因为涉及一些重要的开销(不仅仅是上下文切换,还有刷新缓存等)。

编辑: 您可以在Tutorial中阅读相关内容。具体来说,在第1.2节“福利”中说明了

  

英特尔®线程构建模块旨在提高性能。   大多数通用线程包支持许多不同类型   线程化,例如图形用户中异步事件的线程化   接口。因此,通用包往往是   提供基础的低级工具,而不是解决方案。代替,   英特尔®线程构建模块专注于特定的目标   并行计算密集型工作,交付   更高层次,更简单的解决方案。

  

英特尔®线程构建模块与其他线程兼容   包。因为该库不是为解决所有线程问题而设计的,   它可以与其他线程包无缝共存。

答案 1 :(得分:1)

大规模多线程阻塞行为(std :: cout use)是多线程中的反模式,可能导致不良行为,因为这是错误的做法。此外,TBB保留实施group.run()的权利,但它喜欢它并产生它喜欢的任何线程。如果你只有一个双核心,而你的工作繁重,为什么它会产生两个以上的线程呢?操作系统和其他应用程序将很乐意吃掉剩余的后台时间。