Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/150.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 使用互斥量作为信号量?_C++_Concurrency_C++11_Mutex_Semaphore - Fatal编程技术网

C++ 使用互斥量作为信号量?

C++ 使用互斥量作为信号量?,c++,concurrency,c++11,mutex,semaphore,C++,Concurrency,C++11,Mutex,Semaphore,我需要两个线程以“滴答”模式前进。当使用信号量实现时,这看起来很好: Semaphore tick_sem(1); Semaphore tock_sem(0); void ticker( void ) { while( true ) { P( tick_sem ); do_tick(); V( tock_sem ); } } void tocker( void ) { while( true ) { P( tock

我需要两个线程以“滴答”模式前进。当使用信号量实现时,这看起来很好:

Semaphore tick_sem(1);
Semaphore tock_sem(0);

void ticker( void )
{
   while( true )
   {
      P( tick_sem );
      do_tick();
      V( tock_sem );
   }
}

void tocker( void )
{
   while( true )
   {
      P( tock_sem );
      do_tock();
      V( tick_sem );
   }
}
然而,如果我对互斥体(从技术上讲是一个二进制信号量)做同样的事情,它会有一种奇怪的代码气味

std::mutex tick_mutex;
std::mutex tock_mutex;
tock_mutex.lock();

void ticker( void )
{
   while( true )
   {
      tick_mutex.lock();
      do_tick();
      tock_mutex.unlock();
   }
}

void tocker( void )
{
   while( true )
   {
      tock_mutex.lock()
      do_tock();
      tick_mutex.unlock();
   }
}
我认为这意味着互斥体并不意味着将信息传递给另一个线程。(c++11标准委员会添加了一个虚假的失败尝试_lock来阻止意外的信息传输;§30.4.1/14。)看起来互斥锁是用来同步对变量的访问,然后可以将信息传递给另一个线程

最后,当使用std::condition_变量实现时,它看起来是正确的,但更复杂(tick_vs_tock变量、互斥体和条件变量)。为了简洁起见,我省略了实现,但它实际上是直截了当的

互斥解决方案好吗?还是有什么微妙的问题


有没有一种解决我没有想到的滴答声问题的好模式?

互斥锁不仅仅是一个二进制信号量,它还有一个限制,即只允许锁定线程解锁它

你违反了那条规则

编辑:

发件人:

如果调用线程不拥有 互斥对象

从谷歌搜索的某个网站:

如果出现以下情况,pthread_mutex_unlock()函数可能会失败:

EPERM当前线程不拥有互斥锁


在其他互斥实现中也会发现同样的情况。这是有道理的,因为互斥锁应该保护线程对资源的访问,所以另一个线程不应该能够解锁它。

既然你有理由使用信号量,我认为修复方法是可移植的

这可能不是特别有效(因为每个信号量将使用互斥/condvar对),但您可以在具有自己的信号量的系统(如Posix和Windows)上切换其他实现


显然。恕我直言,我认为至少我们中的一些人能够做到。当然,你可以把自己绑在结上,它们是一个相当低级的工具。但是如果它们是正确的,就没有问题。

BTW:这个问题只是因为C++0x没有
std::semaphore
而double
std::mutex
解决方案比
std::condition\u变量
解决方案更简单。(为什么)它对
解锁()
线程中的互斥锁当前不存在?@Steve这是一个非常好的问题(提示,提示,轻推,轻推)。根据Steve的评论。这真的是一条规则吗?这绝对是个好主意。@deft-我认为这取决于互斥的实现,互斥依赖于系统。通常,解锁其他人的互斥锁不是一个好主意,即使系统允许。@deft_代码:我还没有阅读FDIS的互斥锁部分,但如果这不是一条规则,我会感到惊讶。互斥体有一个所有者,这是其作为同步工具的基本定义的一部分。我同意“太容易出错”的说法很奇怪。互斥体也可能容易出错。锤子也可以。