有一个shared_mutex
为 C++17 计划的类(class)。和shared_timed_mutex
已经在 C++14 中了。 (谁知道他们为什么按这个顺序出现,但无论如何。)然后有一个 recursive_mutex
和 recursive_timed_mutex
从 C++11 开始。我需要的是一个 shared_recursive_mutex
。我是否遗漏了标准中的某些内容,还是我必须再等三年才能获得标准版本?
如果目前没有这样的设施,那么仅使用标准 C++ 来简单(第一优先)和高效(第二优先)实现这样的功能是什么?
最佳答案
Recursive 互斥体的属性使用术语 owner 操作,如果 shared_mutex 没有明确定义:多个线程可能具有 .lock_shared()
同时调用。
假设 owner 作为线程调用 .lock()
(不是 .lock_shared()
!),递归共享互斥锁的实现可以可以简单地从 shared_mutex
派生:
class shared_recursive_mutex: public shared_mutex
{
public:
void lock(void) {
std::thread::id this_id = std::this_thread::get_id();
if(owner == this_id) {
// recursive locking
count++;
}
else {
// normal locking
shared_mutex::lock();
owner = this_id;
count = 1;
}
}
void unlock(void) {
if(count > 1) {
// recursive unlocking
count--;
}
else {
// normal unlocking
owner = std::thread::id();
count = 0;
shared_mutex::unlock();
}
}
private:
std::atomic<std::thread::id> owner;
int count;
};
字段 .owner
需要声明为 atomic,因为在 .lock()
方法中,它会在没有保护并发访问的情况下进行检查。
如果你想递归调用 .lock_shared()
方法,你需要维护 所有者 map ,并且应该使用一些额外的互斥锁来保护对该 map 的访问。
允许具有事件 .lock()
的线程调用 .lock_shared()
使实现更加复杂。
最后,允许线程提前从 .lock_shared()
锁定到 .lock()
是 no-no,因为当两个线程尝试执行该推进时,可能会导致死锁。
同样,recursive shared mutex 的语义非常脆弱,所以最好不要使用它。
关于c++ - 标准 C++ 中的共享递归互斥锁,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36619715/