std::lock_guard
(及其相关)的一个众所周知的问题是,当仅创建一个临时对象时,它无法按预期方式工作。
例如:
std::mutex mtx;
std::lock_guard<std::mutex> {mtx} // temporary object, does not lock the entire scope
std::lock_guard<std::mutex> lck{mtx} // correct
我尝试使用引用限定符来创建一个替代品,以防止创建临时对象(在编译时)。以下代码是徒劳的尝试:
#include <mutex>
template<typename T>
struct my_lock {
T &mtx;
my_lock(T &t) : mtx{t} { lock(); }
~my_lock() { unlock(); }
void lock() & { mtx.lock(); };
void unlock() & { mtx.unlock(); };
};
std::mutex mtx;
int main()
{
my_lock<std::mutex> {mtx}; // A
my_lock<std::mutex lck{mtx}; // B
}
这行不通,所以问题就变成了:
是否有可能以编译器拒绝 A
并接受 B
的方式编写类?
最佳答案
如果你可以使用c++17
,你可以使用带有工厂函数的[[nodiscard]]
属性。
class [[nodiscard]] my_lock{
my_lock()=default;
friend my_lock lock();
};
[[nodiscard]] my_lock lock(){return {};}
int main(){
{ lock(); } //warning for discard return value
{ auto l = lock();}
}
关于c++ - 可以将类对象创建为仅左值吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53966599/