shared_ptr を 1 つずつ破棄しようとしていますが、
それが何を意味するのかわかりませんが、...
myPtr.~__shared_ptr();
決して、決して、これをしないでください。
自動オブジェクト、つまりスタック上に存在し、スコープ外になるとコンパイラによって自動的に破棄されるオブジェクトのデストラクタを実行しています。手動で破壊すると、2 回破壊されます。オブジェクトの寿命を 2 回終わらせることはできません。それはジェームズ ボンドではなく、一度だけ生きます。
同じオブジェクトを 2 回破棄することは未定義の動作です。つまり、奇妙なことが起こり得るということです。未定義の動作をするプログラムから奇妙な結果が得られる理由を尋ねるのは、時間の無駄です。未定義の動作があるため、未定義の動作があると奇妙なことが起こります。何でも起れる。奇妙であり、壊滅的ではないことに感謝する必要があります。
標準は、12.4 [class.dtor] では、この正確なシナリオが未定義の動作であることを明確に指摘しています。
オブジェクトに対してデストラクタが呼び出されると、そのオブジェクトは存在しなくなります。有効期間が終了したオブジェクトに対してデストラクタが呼び出された場合の動作は未定義です (3.8)。[例:自動オブジェクトのデストラクタが明示的に呼び出され、その後、通常はオブジェクトの暗黙的な破棄を呼び出す方法でブロックが残される場合、動作は未定義です。— 最後の例]
さらに悪いことに、の基本クラスのデストラクタを実行しているため、オブジェクトの一部myPtr
のみを破棄しています。つまり、一部が死んで一部が生きているオブジェクトがあり、スコープの終わりにその一部が再び殺されます。いかなる状況においても、それが正しいとは限りません。これまで。
最終的な破壊で use_count() を 0 に設定し、整数のメモリの割り当てを解除することを期待していました。これは何も起こっていないようです。
あなたの結論は間違っています。おそらく起こっているのですが、オブジェクトが破棄されてメモリの割り当てが解除された場合、それを調べようとすると意味のない結果が生じます。ゾンビに名前を尋ねることはできません。ゾンビは「BRAINZZZZ!」と答えます。役に立つことを伝える代わりに。そして、あなたの脳を食べます。今、あなたは死んでいます。ゾンビで遊んではいけません。
また、Neil Kirk が上でコメントしているように、これも間違っています。
int * val = new int(5);
std::shared_ptr<int> myPtr = std::make_shared<int>(*val);
ヒープ上に を作成し、 によって管理されるヒープ上にそのコピーint
を作成します。は同じ値を持つan を所有していますが、何も所有していないため、メモリリークが発生します。おそらく、次のいずれかを行うつもりでした。shared_ptr
shared_ptr
int
*val
val
int * val = new int(5);
std::shared_ptr<int> myPtr(val);
またはおそらくこれ:
int val = 5;
std::shared_ptr<int> myPtr = std::make_shared<int>(val);