我很难决定最好的方法来删除我的派生类。我目前有以下布局:

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~TagList中,我确实在每个标签上调用Tag::releaseMemory();,因为delete上的Tag *只会释放一个Tag而不释放实际的TagWhatever,从而导致内存泄漏。

我想到的另一种选择是在每个派生类中添加一个新的虚拟方法,因此Tag的每个子代都将拥有自己的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
    }
  }
}


并且在运行时动态读取该内容不适用于堆栈上的实例。

我要怎么做才能做到这一点...我不知道

最佳答案

通常,您只需declare a virtual destructor in the base class。这对堆栈和堆分配都很好。如果是多态删除,则编译器会找出真实类型并调用其析构函数。

07-26 00:46