首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用tbb::tbb::parallel_for中排队互斥的简单示例程序不编译

使用tbb::tbb::parallel_for中排队互斥的简单示例程序不编译
EN

Stack Overflow用户
提问于 2013-09-18 02:36:08
回答 2查看 2.2K关注 0票数 2

这里是一个玩具例子,我正在玩,以学习如何使用TBB。并行::operator()应该并行运行,但是它有一个关键区域,一次只能由一个处理器访问,所以它打印的消息不会被加扰。我的问题是,它无法编译,编译器消息对我没有多大帮助。我做错了什么?

此外,这是否被认为是在parallel_for中实现互斥的正确方法?

代码语言:javascript
复制
#include <iostream>
#include <vector>
#include <cmath>
#include <tbb/tbb.h>

typedef tbb::queuing_mutex Mutex;

struct Parallel
{
    Mutex mutex;
    std::vector<int> * values;

    Parallel(std::vector<int> * values_) : values(values_) {}

    void operator()( tbb::blocked_range< unsigned int > & range ) const {
        for(unsigned int i = range.begin(); i < range.end(); ++i) {
            {
                Mutex::scoped_lock lock(mutex);
                if ( (*values)[i] > 40)
                {
                    std::cout << "NO SCRAMBLING ALLOWED!\n";
                    std::cout.flush();
                }
                lock.release();
            }
        }
    }
};

int main() {
    const int someValue = 20000;

    std::vector<int> data(someValue);
    for(int i = 0; i < someValue; ++i) {
        data[i] = std::rand();
    }

    tbb::parallel_for( tbb::blocked_range<unsigned int>(0, data.size()),
                       Parallel(&data) );
}

Bellow是错误消息:

代码语言:javascript
复制
/path-to-src/main.cpp: In member function 'void Parallel::operator()(tbb::blocked_range<unsigned int>&) const':
/path-to-src/main.cpp:20:46: error: no matching function for call to 'tbb::queuing_mutex::scoped_lock::scoped_lock(const Mutex&)'
/path-to-src/main.cpp:20:46: note: candidates are:
In file included from /usr/include/tbb/tbb.h:65:0,
                 from /path-to-src/main.cpp:4:
/usr/include/tbb/queuing_mutex.h:80:9: note: tbb::queuing_mutex::scoped_lock::scoped_lock(tbb::queuing_mutex&)
/usr/include/tbb/queuing_mutex.h:80:9: note:   no known conversion for argument 1 from 'const Mutex {aka const tbb::queuing_mutex}' to 'tbb::queuing_mutex&'
/usr/include/tbb/queuing_mutex.h:77:9: note: tbb::queuing_mutex::scoped_lock::scoped_lock()
/usr/include/tbb/queuing_mutex.h:77:9: note:   candidate expects 0 arguments, 1 provided
/usr/include/tbb/queuing_mutex.h:66:11: note: tbb::queuing_mutex::scoped_lock::scoped_lock(const tbb::queuing_mutex::scoped_lock&)
/usr/include/tbb/queuing_mutex.h:66:11: note:   no known conversion for argument 1 from 'const Mutex {aka const tbb::queuing_mutex}' to 'const tbb::queuing_mutex::scoped_lock&'
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2013-09-18 14:50:47

tbb::parallel_for的设计目的是不按编写的方式编译示例。这是为了防止代码中的漏洞。tbb::parallel_for的范围形式通过值将函子复制到多个任务对象中。因此,每个任务都将有一个互斥体的单独副本,因此互斥体不会提供预期的同步。

修复代码的方法是在struct并行的外部声明互斥体,并通过指针传递它,类似于“值”的指针。

票数 1
EN

Stack Overflow用户

发布于 2013-09-18 15:12:00

一切都是正确的,除了mutex必须是mutable才能在锁中使用。此外,释放锁是不必要的。

代码语言:javascript
复制
typedef tbb::queuing_mutex Mutex;

struct Parallel
{
    mutable Mutex mutex;              // mutable so that we can use it in const member
    std::vector<int> * values;

    Parallel(std::vector<int> * values_) : values(values_) {}

    // note: this is a const member
    void operator()( tbb::blocked_range< unsigned int > & range ) const
    {
        for(unsigned int i = range.begin(); i < range.end(); ++i)
        {
            Mutex::scoped_lock lock(mutex);       // requires non-const argument
            if ( (*values)[i] > 40)
            {
                std::cout << "NO SCRAMBLING ALLOWED!\n";
                std::cout.flush();
            }
            // no need to release the lock: the destructor will do that for you
        }
    }
};

当然,您也可以将成员函数设置为非const。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18862975

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档