web-dev-qa-db-ja.com

C ++ 11 unique_ptrとshared_ptrはお互いの型に変換できますか?

C++ 11標準ライブラリは、std::shared_ptrからstd::unique_ptrへ、またはその逆に変換するユーティリティを提供しますか?これは安全な操作ですか?

72
Hind Forsum

std::unique_ptrは排他的所有権を表すC++ 11の方法ですが、その最も魅力的な機能の1つは、std::shared_ptrに簡単かつ効率的に変換できることです。

これは、std::unique_ptrがファクトリ関数の戻り値型として非常に適している理由の重要な部分です。ファクトリ関数は、呼び出し元が返すオブジェクトに対して排他的所有権セマンティクスを使用するかどうか、または共有所有権(つまり、std::shared_ptr)がより適切かどうかを知ることができません。 std::unique_ptrを返すことで、ファクトリーは呼び出し元に最も効率的なスマートポインターを提供しますが、呼び出し元がより柔軟な兄弟に置き換えることを妨げません。

std::shared_ptrからstd::unique_ptrは許可されていません。リソースのライフタイム管理をstd::shared_ptrに切り替えても、気が変わることはありません。参照カウントが1であっても、たとえばstd::unique_ptrで管理するためにリソースの所有権を取り戻すことはできません。

参照:効果的なModern C++。 42 C++ 11およびC++ 14の使用を改善する特定の方法。スコット・マイヤーズ。

つまり、std::unique_ptrstd::shared_ptrに簡単かつ効率的に変換できますが、std::shared_ptrstd::unique_ptrに変換することはできません。

例えば:

std::unique_ptr<std::string> unique = std::make_unique<std::string>("test");
std::shared_ptr<std::string> shared = std::move(unique);

または:

std::shared_ptr<std::string> shared = std::make_unique<std::string>("test");
117
chema989