2011-02-03 6 views
0

私は派生クラスを削除する最良の方法をここで決定するのに非常に苦労しています。私は現在、次のようなレイアウトを持っている:どこを削除しますか?

class Tag { 
    // Stuff 
    // [...] 
    void releaseMemory(Tag *t); 
}; 

class TagByte : public Tag { /* [...] */ }; 
class TagShort : public Tag { /* [...] */ }; 

Tag::releaseMemory(Tag *t) { 
    switch (t->getType()) { 
     case TAG_BYTE: delete (TagByte *)t; return; 
     case TAG_SHORT: delete (TagShort *)t; return; 
     // [...] many more 
    } 
} 

は、私がこれをやっている理由は、異なる種類のタグが含まれていますTagCompoundのようなより複雑なタグがあるということです、そして、それらのすべてがTag *として保存されます。デストラクタの内部~TagCompound~TagListdeleteTagを解放するだけで、実際のTagWhateverは解放されず、メモリリークが発生するため、すべてのタグでTag::releaseMemory();を呼び出します。

私が考えていたもう1つの選択肢は、すべての派生クラスに新しい仮想メソッドを追加することでした。したがって、Tagのすべての子は、スーパークラスに1つではなくreleaseMemory()であることになります。

は、その後、私はこのため、私はまた、より良い解決策を見つけることができませんでしたヒープ対象である複合型TagCompoundTagListに渡されたすべてのものを想定して、私はすでに設計レベルでの不良をオフ始めているかどうかを疑問に思いました

TAG_Compound("Root"): 4 entries 
{ 
    TAG_String("Name"): Test 
    TAG_Short("SomeNumber"): 21 
    TAG_Double("..."): 9000.5 
    TAG_Compound("Eek!"): 2 entries 
    { 
    TAG_String("Marco"): Polo 
    TAG_List("Names"): 3 entries of type String 
    { 
     TAG_String: Hello 
     TAG_String: World 
     TAG_String: Segfault 
    } 
    } 
} 

そして、実行時に動的にスタック上のインスタンスとうまく再生されないことを読んだ:全体の構築物は、(単にバイナリおよびなど冗長ではない)、このようなもののためのパーサーの一部です。

私はこれを行うために何ができますか...わかりません..エレガントですか?

+0

なぜ、オーバーレイされたreleaseMemoryメンバー関数を使用しないのですか?私はあなたの質問が正しいとすればそれで十分だろうと思う。 – Arunmu

答えて

5

通常、あなたはただdeclare a virtual destructor in the base classです。これは、スタックとヒープの両方の割り当てでうまくいく。多態的な削除の場合、コンパイラは真の型を見つけ出し、そのデストラクタを呼び出します。

+0

それは実際に私がやっていたことよりも複雑ではありません:) – LukeN

1

このデザインは、カプセル化のアイデアを本当に破ります。タグはTagByteが存在することを決して知らないはずです。 Tagのデストラクタは、各派生クラスのデストラクタと同じように、バーチャルとしてマークする必要があります。適切なデストラクタの各レベルの割り当てられた変数を解放します。破壊時には、メモリリークのない正しい順序ですべてがクリーンアップされます。私の気持ちは、このデザインが最初から悪いことです。あなたはデストラクタと継承について読まなければなりません。

+0

うん、私もそうだと思ったので、私はよく知っている人によく聞くことにしました! – LukeN

1

実際には、C++はこれに非常に洗練されたソリューションを提供します - 仮想デストラクタ。さらに、すべての多型には1つが必要です。 GCCにもこの警告レベルは-Wnon-virtual-dtorです。

関連する問題