为什么要将mutex作为参数传递给线程调用的函数?

pol*_*pts 8 c++ multithreading boost mutex

在某些地方,我看到人们创建一个线程池并创建线程并使用这些线程执行一个函数.调用函数boost :: mutex时通过引用传递.为什么这样做?我相信你可以在被调用函数本身中声明一个互斥锁,或者可以声明为类成员或全局变量.有人可以解释一下吗?

例如

   myclass::processData()
   {
         boost::threadpool::pool pool(2);
         boost::mutex mutex;

         for (int i =0; data<maxData; ++data)
             pool.schedule(boost::bind(&myClass::getData, boost_cref(*this), boost::ref(mutex)));
    }
Run Code Online (Sandbox Code Playgroud)

然后,

    myClass::getData(boost::mutex& mutex)
    {
         boost::scoped_lock(mutex)    // Why can't we have class member variable mutex or                                     
                                      //local mutex here
        //Do somethign Here
}
Run Code Online (Sandbox Code Playgroud)

Jas*_*son 10

Mutex是不可复制的对象,虽然它们可以是类的成员,但它会使父类的复制能力大大复杂化.因此,如果许多类实例需要共享相同的数据,则一种优选方法是将互斥体创建为静态数据成员.否则,如果只需要将互斥锁锁定在类本身的实例中,则可以创建指向互斥锁的指针作为非静态数据成员,然后该类的每个副本都拥有它自己动态分配的互斥锁(和如果是要求,则保持可复制).

在上面的代码示例中,基本上发生的是通过引用将全局互斥锁传递到线程池中.这使得共享相同内存位置的所有线程能够使用完全相同的互斥锁在该内存上创建独占锁,但不需要管理互斥锁本身的不可复制方面的开销.此代码示例中的互斥锁也可能是类的静态数据成员,myClass而不是通过引用传入的全局互斥锁,假设每个线程都需要锁定一些可从每个线程全局访问的内存.

本地互斥锁的问题在于它只是本地可访问的互斥体版本...因此当一个线程锁定互斥锁以共享一些全局可访问的数据时,数据本身不受保护,因为每个其他线程都会拥有它拥有可以锁定和解锁的本地互斥锁.它打破了互斥的整个过程.

  • ...这一切都取决于你的对象的定义是什么(语义上)在大多数情况下,互斥体不构成对象状态的一部分,但是是一个实用程序,以确保不能看到类的真实状态在多线程环境中使用时的中间错误(不变量). (2认同)