23

我有一个关于使用(或类似的作用域锁)和使用语句boost::lock_guard中应受锁保护的变量的问题。return

销毁本地对象和复制返回值的顺序是怎样的?返回值优化如何影响这一点?

例子:

Data Class::GetData()
{
    boost::lock_guard<boost::mutex> lock(this->mMutex);
    return this->mData;
}

这是否正确(如果 mData 是受 mMutex 保护的变量)?或者我是否必须使用本地范围和临时范围,如下例所示:

Data Class::GetData()
{
    Data ret;
    {
        boost::lock_guard<boost::mutex> lock(this->mMutex);
        ret = this->mData;
    }
    return ret;
}
4

3 回答 3

29

在您的第一个示例中,直接返回是正确的。返回值是在局部变量被销毁之前构造的,因此在锁被释放之前。

于 2010-10-04T15:38:09.103 回答
3

销毁本地对象和复制返回值的顺序是怎样的?

通常,堆栈对象以与创建相反的顺序被销毁。如前所述,您指定的两种方法都将提供所需的行为。

返回值优化如何影响这一点?

RVO 在这里不应该是一个问题 - 所有这些都是将输出对象直接构建到堆栈帧缓冲区中 - 避免创建命名临时对象的开销(如上面的第二个示例)。这是在调用本地析构函数之前完成的。

最好使用上面示例 1 中的代码。

于 2010-10-04T16:09:35.940 回答
0

Both pieces are equivalent. In fact for case #1 - C++ compiler will create structure described in case #2. So #1 is preferable.

于 2010-10-04T15:41:42.673 回答