众所周知,std :: unique_lock可能会在调用析构函数时释放互斥锁。
考虑下面源代码中第8行的行为lck.unlock()
,我的问题是在函数返回之前解锁互斥是否会增加并发性?
MessageWrapper ServerLeftCommunicator::receive() {
unique_lock<mutex> lck(recvMsgQCvMtx_);
recvMsgQCv_.wait(lck, [this] {
return ! recvMsgQ_.empty();
});
auto wrapper = recvMsgQ_.front();
recvMsgQ_.pop();
lck.unlock();
return wrapper;
}
谢谢。
答案 0 :(得分:7)
没有。返回之前发生的第一件事是析构函数将调用unlock
。这是将被破坏的唯一局部变量,假设正在进行返回值优化并且wrapper
的类型实际上是MessageWrapper
。
在这种情况下,明确地调用unlock
希望您获得一些好处将被视为不良风格。
也许,如果在函数返回之前发生了其他非平凡的操作,您可能会考虑这样做。但是将特定于锁的内容放在范围块中而不是显式解锁会更合适。与任何并发优化一样,始终将锁定范围降至最低。
答案 1 :(得分:1)
你没有真正显示足够的代码,我们可以估计各种操作的成本。
但是,在我看来,您的代码可以从“命名返回值优化”中受益,因为始终返回对象wrapper
。如果它被推导为MessageWrapper
,那么编译器将直接在该目标返回值中构造wrapper
。这意味着返回甚至不会有复制返回值的成本。
在这种情况下,提前解锁几乎没有任何好处,因为返回的成本远低于复制对象的成本。