假设我有这样的代码:
#include "boost/thread/mutex.hpp"
using boost::mutex;
typedef mutex::scoped_lock lock;
mutex mut1, mut2;
void Func() {
// ...
}
void test_raiicomma_1() {
lock mut1_lock(mut1);
Func();
}
void test_raiicomma_2() {
(lock(mut1)), Func();
}
void test_raiicomma_3() {
(lock(mut1)), (lock(mut2)), Func(); // Warning!
}
int main()
{
test_raiicomma_1();
test_raiicomma_2();
test_raiicomma_3();
return 0;
}
如果函数test_raiicomma_1
() 是从多个线程调用的,它会锁定一个互斥体以防止任何其他线程同时调用Func()
。互斥体在构造变量时被锁定,mut1_lock
在超出范围并被破坏时释放。
这工作得很好,但作为一种风格,需要为持有锁的临时对象命名让我很恼火。该函数test_raiicomma_2()
试图通过初始化锁对象并Func()
在一个表达式中调用该函数来避免这种情况。
直到表达式结束才调用临时对象析构函数是否正确, afterFunc()
已返回?(如果是这样,你认为使用这个成语是否值得,或者在单独的语句中声明锁总是更清楚?)
如果该函数test_raiicomma_3()
需要锁定两个互斥锁,那么互斥锁在调用之前会按顺序锁定Func()
,然后释放,但不幸的是可能会以任一顺序释放,这是否正确?