• ベストアンサー

【C++】new/deleteについて

deleteについていまいち解らないことがいくつかあります 1 deleteしたポインタを再びnewで確保して使用してもいいのか 2 newしたものは(例えば)関数を抜ける際必ずdeleteするべきなのか それとも抜ける時に自動的に解放されるのか 3 動的オブジェクトの場合も中で動的確保したものを全てdeleteしてからdeleteするべきなのか 何卒よろしくお願いいたします。

質問者が選んだベストアンサー

  • ベストアンサー
回答No.1

1: かまいません 2: 使い終わったら必ずdelete。  自動的にdeleteして欲しいならそれなりのからくりが必要です。 3: YES. [2]より自明。

sirooni
質問者

お礼

ありがとうございます。

関連するQ&A

  • C++ newについて

    お世話になっております。C++初心者です。 newについて質問です。 newして動的にメモリを確保したものはdeleteにて解放処理を 行わないとメモリリークしてしまうのはわかっているのですが、 newした動的メモリに再度newをするとどうなるのでしょうか? また、複数回deleteもせずにnewし続けたあとに deleteをした場合はすべて解放されるのでしょうか? 少し気になったので質問してしまいました。 よろしくお願いいたします。

  • delete演算子によるメモリ解放について

    MFC MDIプログラミングで、 Genericクラスで点、線、面クラスを作って、 オブジェクトを組み合わせて 3次元図形を作っています。 図形を削除する際、 delete演算子で各オブジェクトの メモリ解放をプログラムしています。 例) delete m_pLine; delete m_pSurface; しかしながら、これらポインタの中には、 アルゴリズム上、既にdeleteされているものもあるため、 既にdeleteしたオブジェクトを更に deleteしようとして 実行時エラーを生じてしまいます。 deleteする前に、 当該ポインタが既にdeleteされているかどうか 判定する関数等あれば if文で回避できると思うのですが、 何か良い方法がありますでしょうか? よろしくお願いします。

  • C++のnewで確保した領域について

    こんにちわ。C++を勉強し始めた者です。 new演算子を使ってインスタンスを生成した場合、それはスタックではなくヒープ領域に確保され、不要になったらdeleteを使って領域を解放しなければいけない認識です。 C++の初心者向けサンプルコードを見ていて疑問があったので質問させてください。 (例)クラスA.cpp ======================== #include <Car> #include <Garage> ~略~ クラスAのコンストラクタ{ Car *mycar = new Car("プリウス"); addGarage( mycar ); } クラスAのデストラクタ{ } ======================== 上記のような実装のクラスAがあったのですが、コンストラクタでCarクラスのインスタンス生成をして、オート変数の*mycarに格納して、Garageの公開関数に渡しています。 質問1:このクラスAをインスタンス生成した場合、コンストラクタで確保したヒープ領域は、プログラム終了時まで解放されない認識であっていますか? 質問2:オート変数の*mycarはコンストラクタからreturnした時点で解放されてしまうので、今のままではデストラクタでヒープ領域をdeleteできない認識であっていますか? 質問3:newで生成したインスタンスへのポインタは、その関数内でdeleteしない場合、メンバ変数やstatic変数、グローバル変数に格納しなければdeleteできなくなるという理解であっていますか? 質問4:C++のコードでnewした戻り値をオート変数に格納するプログラムは通常使うことはあるのですか?

  • C++:構造体:newで入れ子:deleteは?

    C++で以下のような構造体を使っています。(本当は他にもメンバが有ります) // ----- typedef struct{  int *npMember; }Test_t; // ----- これをクラスのメンバ変数で // ----- Test_t *m_tpTestStruct; // ----- とし、関数の中で // ----- m_tpTestStruct = new Test_t[10]; for (int i = 0; i < 10; i++) {  m_tpTestStruct[i].npMember = new int[100]; } // ----- というようにメモリを割り当てています。 これを解放する時は、 // ----- for (int i = 0; i < 10; i++) {  delete [] m_tpTestStruct[i].npMember; } delete [] m_tpTestStruct; // ----- で、良いのでしょうか? それとも、他の書き方が必要なのでしょうか?

  • delete[]と、delete演算子の明確な違いとその使い分けについて

    C++の delete[]と、delete演算子の明確な違いとその使い分けについて 型* ptr = new 型[要素数]; でnewしたものについては、 delete[] ptr; にて、開放 型* ptr = new 型(); でnewしたものは、 delete ptr; するものだと、覚えてました、 特に深くは考えていなかったのですが。 std::auto_ptr<T> では、内部的には、delete[]ではなく deleteをしているという文章を見ました。 { std::autoptr<型A> iptr; iptr = new 型A; } のようなときは いいのですが・・・ { std::auto_ptr<char> cptr; cptr = new char[n+1]; } のようなときは、 動的配列なので、内部的に delete ptr; になってしまいます。 このように、テンプレートクラスを自作するときに 実際の特殊な型が決定されるまで、 deleteで、いくのかdelete[]でいくのか決定できないのはつらそうです。 そこで、deleteと、delete[]の正しい意味を 知りたいのですが。 Javaや、.NETには、配列オブジェクトというものが あります。 C++で、 new char[n+1]; は配列オブジェクトでしょうか? だとすると、delete[]は 右に来たものが配列オブジェクトなら、 Lengthを(こんなものがあるとして)調べて 1つづつ、まわして、deleteのほうを使ってひとつひとつ開放していく。 右に来たものが配列オブジェクトでなければ deleteと同じ振る舞いをする。 という動きが物理的に考えれそうで。 delete[]と書いておけば、状況に応じて、 動的配列なら全要素サーチして、開放そうでなければ deleteという風に、勝手に自動でそうしてくれるなら、 どんなときでも、delete[]にするようにコードを書いておけばよさそうです。。 実際のところどうなんでしょうか? deleteと、delete[]の明確な意味の違いと、 使用方法の違いについて教えてください。

  • C++ 構造体のnew

    こんにちは C++のプログラムで 構造体 KOUZOUTAIの領域をx個分確保したいと思っています。 構造体のメンバにはポインタは使われていません。 KOUZOUTAI *kouzoutai1; int count = 5; kouzoutai1 = new KOUZOUTAI[count]; delete[] kouzoutai1; CLASSを使用していませんが、問題ないでしょうか?

  • newされたポインタとdeleteされるポインタが…

    いま私は、std::mapを使って、newされたポインタ(メモリの先頭アドレス)をkeyとして記録し、newされた場所のファイルや行番号、サイズ、何回目のnewか、などなどをvalueとして構造体にまとめて保存してデバッグなどに役立て、deleteされると同時にこの情報を破棄し、最後にすべて破棄されているかどうかを調べる(メモリリークのチェック)という機構を作っています。 ですが、keyとなっているメモリのアドレスは、多重継承や仮想継承とキャストの組み合わせ次第では、newされた時点のものとdeleteされる時点のもので異なっている場合があるため、情報を破棄することができず、行き詰ってしまいました。(無論、delete以外にも情報を引き出す際に影響が…) deleteするポインタから、そのポインタがnewで作成されたときのメモリの先頭アドレスを求める方法はないでしょうか? 以下に問題の部分だけ抽出したようなコードを挙げます。 ---------------- #include <stdio.h> class CLS1{ public: int x,y,z; virtual ~CLS1(){} }; class CLS2{ public: int x,y; virtual ~CLS2(){} }; class CLS3:public CLS1, public CLS2{ public: int x; virtual ~CLS3(){} }; void print(void* p){printf("%p\n",p);} template<typename T> T* create(T* p){ // ここで、たとえば 00854880 と記録されたとして… print(p); return p; } template<typename T> void releace(T* p){ // ここでも 00854880 と記録されてほしいが、 // 00854890 と記録されてしまう。 // この場所で 00854880 と同じインスタンスであることを確かめる方法はないでしょうか? print(p); delete p; } int main(){ CLS2* x = create(new CLS3); // 多重継承しているため、 00854890 と記録される。 print(x); release(x); return 0; }

  • newしないオブジェクトについて

    C++で オブジェクト生成時、NEW しない場合、 どこにメモリ領域が作られているのでしょうか? また、newはmallocと同じで、動的にメモリを確保ということはわかるのですが、 では、newしない場合、静的ということになるのでしょうか? そうだとすると、静的なオブジェクトとは一体どのようなものをいうのでしょうか? よろしくおねがいします。

  • C++のnewの使い道

    最近C++を勉強しているのですが、new演算子はどういうときに使うべきでしょうか? メモリを動的確保できるのはわかります。 Cのmallocのようなものと考えていいのでしょうか? つまり、関数内でメモリを確保してそのアドレスを返すとか、コンパイル時に不明なサイズのメモリを実行時に確保するとか、任意のタイミングでメモリを開放したい場合などに使うものでしょうか。 ある参考書を読んでいると「引数つきコンストラクタを呼び出す場合はnewでインスタンス生成する」と書いてありました。 デフォルトコントラスタならnewなし、引数付きならnewあり、ということらしいです。 なぜこんなことをする必要があるのでしょうか?

  • newで生成したものをdelete[]で破棄するのは間違い?

    int* p = new int(0); と確保したものを、普通は delete p; と書いて破棄しますが、代わりに delete[] p; と書いて破棄しても問題はないのでしょうか? 非常に悪いコードなのですが..... <1>: int* p = new int(0); <2>: int* p = new int[x]; //xはどこかで値を設定済み このうちの、1か2かのどちらかでpに対して領域を割り付けた場合に、どちらもdelete[]で破棄しても問題ないか? という意味の質問です。 コンパイルして実行しても特にエラーを吐くことはありませんでしたが非常に心配です。

専門家に質問してみよう