多态和析构函数

时间:2013-06-18 03:51:18

标签: c++ destructor polymorphism

我刚写了一些代码,我试图理解对象是如何被多态破坏的。

#include <iostream>

struct Base {
    virtual ~Base() {
        std::cout << "base destructed\n";
    }
};

struct Derived : public Base{
virtual ~Derived() {
    std::cout << "derived destructed\n";
}
};

int main() {
  Derived der;
  Base bases1[2], bases2[2], bases3[2], bases4[2];
  //case 1
  new(bases1) Derived(der);
  std::cout << "((Base*)bases1)->~Base();\n";
  ((Base*)bases1)->~Base();
  //case 2
  new(bases2) Derived(der);
  std::cout << "\nbases2->~Base();\n";
  bases2->~Base();
  //case 3
  new(bases3) Derived(der);
  std::cout << "\nbases3[0].~Base();\n"; 
  bases3[0].~Base();
  //case 4
  new(bases4) Derived(der);
  std::cout << "\n(*bases4).~Base();\n";    
  (*bases4).~Base();

  getchar();
  return 0;
}

我对上述代码的了解:

  1. 在case 1中,bases1指向Derived对象的开头(包括一个vptr),它是一个基指针,所以它就像我们在基指针上删除的通常情况一样(我的意思是破坏)。 LI>
  2. 在案例2中,bases2是一个数组名称,但在某些情况下,我们可以将其视为指向第一个对象的指针,因此案例2应该给出与案例1相同的结果吗?
  3. 案例3和案例4是相同的,它们都取消引用第一个对象,它具有类型:Base,然后在其上调用析构函数。
  4. 这些代码非标准且危险,但我只想弄清楚它是如何在指定的编译器上运行的(visual studio 2012)。
  5. 输出:

    ((Base*)bases1)->~Base();
    derived destructed
    base destructed
    
    bases2->~Base();
    
    bases3[0].~Base();
    base destructed
    
    (*bases4).~Base();
    base destructed
    

    我想知道的事情:

    1. 在案例2中,没有任何东西被破坏,可能的原因是什么?编译器优化?
    2. 在casse 3和case 4中,只有基地被破坏了,怎么样?对象切片?
    3. 编辑:

      以下是我从反汇编窗口获得的内容:

       ((Base*)bases1)->~Base();
      00D96CF9  mov         esi,esp  
      00D96CFB  push        0  
      00D96CFD  mov         eax,dword ptr [bases1]  
      00D96D00  lea         ecx,[bases1]  
      00D96D03  mov         edx,dword ptr [eax]  
      00D96D05  call        edx  
      00D96D07  cmp         esi,esp  
      00D96D09  call        __RTC_CheckEsp (0D91992h)
      
        bases2->~Base(); //empty
      
        bases3[0].~Base();
      00D96DB0  push        0  
      00D96DB2  mov         eax,4  
      00D96DB7  imul        eax,eax,0  
      00D96DBA  lea         ecx,bases3[eax]  
      00D96DBE  call        Base::`vector deleting destructor' (0D91A0Ah) //array delete?
      
        (*bases4).~Base();
      00D96E14  push        0  
      00D96E16  mov         eax,4  
      00D96E1B  imul        eax,eax,0  
      00D96E1E  lea         ecx,bases4[eax]  
      00D96E22  call        Base::`vector deleting destructor' (0D91A0Ah)  //aray delete?
      

      我无法阅读汇编程序,有人能给我一个合理的解释吗?

1 个答案:

答案 0 :(得分:0)

new(bases1) Derived(der);

未定义的行为。 bases1Base的数组。将Derived类型的对象填入其中​​并没有做任何有意义的事情。