2012-02-25 22 views
19

可能性の重複:
Deleting pointers in a vectorstd :: vectorはオブジェクトへのポインタのデストラクタを呼び出しますか?

私はstd::vectorが破壊されたとき、それはその項目のそれぞれのデストラクタを呼び出します知っています。それはオブジェクトへのポインタののデストラクタを呼び出しますか?

vector<myclass*> stuff; 

stuffが破壊された場合、stuff内のポインタが指す個々のオブジェクトは破壊されますか?

+0

[boost :: ptr_vector ](http://www.boost.org/doc/libs/1_49_0/libs/ptr_container/doc/ptr_vector.html) –

答えて

30

どうstd::vectorオブジェクトに尖ったを、破壊する方法を知ることになっていますか? deleteを使用する必要がありますか? delete[]free?いくつかの他の機能?指し示されたオブジェクトが実際に動的に割り当てられていること、またはそれがOne True Ownerであり、それらを破壊する責任があることを、どのようにして知ることになっていますか?

std::vectorが指し示されたオブジェクトのOne True Ownerである場合は、std::unique_ptrを使用して、潜在的にカスタムのDeleterを使用してオブジェクトのクリーンアップを処理します。

+1

「std :: vector」にダンディーになる要素のための破壊関数をとるコンストラクターです。これは、レガシーまたはC APIにとって便利です。しかし、どうにかしてより良いやり方は、この種のリソースをRAIIクラスでラッピングすることです。 – wilhelmtell

+1

@wilhelmtellあなたはそれのためのカスタムアロケータを書くことができます:)または 'unique_ptr'にカスタムdeleter関数を与えます。 –

+0

@SethCarnegieええ、それはコメントを投稿してから数秒後です。思考の前に話す、いつも私に起こる。 :-S – wilhelmtell

5

いいえ;自動オブジェクトへのポインタを格納した場合はどうなりますか?

vector<T*> v; 
T tinst; 
v.push_back(&tinst); 

ベクトルは、ポインタが指すオブジェクトのデストラクタを呼び出した場合、自動的にオブジェクトが二度破壊されるだろう - ベクトルがスコープ外に行ったときに一度、それがスコープ外に行ったときに一度、と。また、deleteで割り振り解除されていない場合はどうなりますか?どんな状況においても適切に行動することはできません。

オブジェクトがすべて動的に割り当てられている場合は、newが割り当てられている場合は、ベクトルとdelete各ポインタを手動で反復処理する必要があります。また、あなたはスマートポインタのベクトルを作成することができますオブジェクトの割り当てを解除し、ポインタで指される:

vector<shared_ptr<T>> v; 
v.push_back(new T); 
+0

Hm。 2番目の言葉は、「ため」と誤解を招くと思います。 pointeesを削除しないことを正当化する責任は、ベクトル上にありません。むしろ、OPは、なぜコンテナ*がポインタ型の要素を異なって扱うべきかを説明しなければなりません。それが立てば、答えはシンプルな「いいえ」になる可能性があります。 –

+1

@KerrekSBが削除されました:) –

15

をあなた自身、ベクトルはその要素に対してデストラクタを呼び出して行い、正しく言ったように。したがって、あなたの例では、ベクトル "ポインタのデストラクタ"を呼び出します。ただし、ポインタ型にはデストラクタがないことに注意する必要があります。デストラクタを持つことができるのはクラス型だけです。ポインタはクラスではありません。したがって、std::vectorは、ベクトルに格納されたポインタオブジェクトに疑似デストラクタ呼び出し構文を適用すると言うのがより正確です。結果として無操作のポインタ型の場合、つまり何もしない場合。

これは、あなたの質問の第2の部分にも答えます:myclassオブジェクトがポインターによって指し示されているかどうかが破壊されるかどうか。いいえ、彼らは破壊されません。

また、「ポインタのデストラクタを呼び出す」(質問の最初の部分)は、「指摘されたオブジェクトを破棄する」(質問の第2部分)と同じことだと思われるようです。実際には、これらは全く別の2つの無関係なものです。

前者から後者へのリンクを作成するために、ベクトルが指し示すオブジェクトを破壊するようにするには、通常の生のmyclass *ポインタとは対照的に、ある種の「スマートポインタ」からベクトルを構築する必要があります。ベクトルは自動的に "スマートポインタ"のデストラクタを呼び出し、これらのデストラクタは順番に、先のオブジェクトを破壊します。この "リンク"は、 "スマートポインタの"デストラクタの内部でのみ明示的に実装することができます。そのため、通常の生ポインタはここでは役に立ちません。

+0

実際に正確にしたいのであれば、 'std :: vector'は何も破壊しません。アロケータは –

+0

+1ハハ、とても良い、スポットオンです。 –

+0

ポインタが特別なケースでない理由を示すので、これは受け入れられた答えでなければなりません。 –

関連する問題