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();}
}
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加