Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
.net 虚拟析构函数_.net_Oop - Fatal编程技术网

.net 虚拟析构函数

.net 虚拟析构函数,.net,oop,.net,Oop,有人能给我解释一下虚拟析构函数的概念吗?在dotnet中如何处理它? < p>如果你指的是C++。< /P> 析构函数必须始终声明为虚拟 为什么?? 因为当对象被“破坏”时,它必须清除我们在代码中引用的对象的资源 请参阅此示例以了解: Class A; Class B: Public A { int *pVar }; A* x = new B(); delete x ) 在这种情况下,如果B的析构函数未声明为virtual,则将调用的析构函数是A的析构函数,因此不会释放pVar。 希望这

有人能给我解释一下虚拟析构函数的概念吗?在dotnet中如何处理它?

< p>如果你指的是C++。< /P> 析构函数必须始终声明为虚拟

为什么?? 因为当对象被“破坏”时,它必须清除我们在代码中引用的对象的资源

请参阅此示例以了解:

Class A;
Class B: Public A { int *pVar };


A* x = new B();

delete x
)

在这种情况下,如果B的析构函数未声明为virtual,则将调用的析构函数是A的析构函数,因此不会释放pVar。 希望这是清楚的

编辑:如果这回答了您的问题,请将其标记为答案或至少向上投票


<> > Edg2>强:这篇Wiki描述得很好。如果你引用C++,

< P> 析构函数必须始终声明为虚拟

为什么?? 因为当对象被“破坏”时,它必须清除我们在代码中引用的对象的资源

请参阅此示例以了解:

Class A;
Class B: Public A { int *pVar };


A* x = new B();

delete x
)

在这种情况下,如果B的析构函数未声明为virtual,则将调用的析构函数是A的析构函数,因此不会释放pVar。 希望这是清楚的

编辑:如果这回答了您的问题,请将其标记为答案或至少向上投票


EDIT2:这个wiki描述得非常好。

概念是继承行中直到根(
对象
)的每种类型都有机会进行清理。它基本上与普通虚拟方法的概念相同

在.NET中,方法基本上就是这样。但是请注意,由于.NET是一个托管环境,其垃圾收集器不确定,因此调用
Finalize()
方法的时刻也不确定


如果这回答了您的问题,请接受它作为答案。

概念是继承行中直到根(
对象
)的每个类型都有机会进行清理。它基本上与普通虚拟方法的概念相同

在.NET中,方法基本上就是这样。但是请注意,由于.NET是一个托管环境,其垃圾收集器不确定,因此调用
Finalize()
方法的时刻也不确定

如果这回答了您的问题,请接受它作为答案。

关于析构函数和终结器,请参阅Eric Lippert的伟大文章


关于析构函数和终结器,请参阅Eric Lippert的一篇伟大的文章,下面的程序解释了虚拟析构函数的需要

#include <iostream>
#include <conio.h>
using namespace std;

class Base
{
   public:
      Base()
          { cout<<"Constructor: Base"<<endl;}
      ~Base()
          { cout<<"Destructor : Base"<<endl;}

};
class Derived: public Base
{     
   public:
       Derived()
              { cout<<"Constructor: Derived"<<endl;}
       ~Derived()
              { cout<<"Destructor : Derived"<<endl;}

};
void main()
{
    Base *Var = new Derived();      
    delete Var;
    _getch();       
}
在上述情况下,不会调用派生对象的析构函数。因此,如果将基类的析构函数设置为虚拟的,那么输出将如下所示:

Constructor: Base
Constructor: Derived
Destructor : Base
Constructor: Base
Constructor: Derived
Destructor : Derived
Destructor : Base

下面的程序解释了虚拟析构函数的需要

#include <iostream>
#include <conio.h>
using namespace std;

class Base
{
   public:
      Base()
          { cout<<"Constructor: Base"<<endl;}
      ~Base()
          { cout<<"Destructor : Base"<<endl;}

};
class Derived: public Base
{     
   public:
       Derived()
              { cout<<"Constructor: Derived"<<endl;}
       ~Derived()
              { cout<<"Destructor : Derived"<<endl;}

};
void main()
{
    Base *Var = new Derived();      
    delete Var;
    _getch();       
}
在上述情况下,不会调用派生对象的析构函数。因此,如果将基类的析构函数设置为虚拟的,那么输出将如下所示:

Constructor: Base
Constructor: Derived
Destructor : Base
Constructor: Base
Constructor: Derived
Destructor : Derived
Destructor : Base

当然,你知道虚拟方法是如何工作的吗?如果没有,读一些书。阅读本文:了解虚拟方法是如何工作的。如果您想了解为什么析构函数需要是虚拟的,这一点至关重要。在这篇文章的后半部分是关于虚拟析构函数的解释。如果析构函数必须始终声明为虚拟的,那么为什么将一个析构函数声明为非虚拟的是合法的呢?我可以想到的一个原因是——如果不使用多态性,那么将析构函数定义为虚拟将强制创建vtable(在C++中,只有在类中有一个或多个虚拟方法时才创建VTALE)C++允许程序员只根据需求激活多态性机制,因此如果不需要,则没有理由声明Dor Tor虚拟化。编译器知道是否派生出一个类,所以所有这些都可以是自动化的。只是我们坚持单独编译单元。这对编程活动有很高的成本。Victivity…当然,你知道虚拟方法是如何工作的吗?如果不知道,请阅读一些文章。阅读以下内容:了解虚拟方法是如何工作的。如果你想了解为什么析构函数需要是虚拟的,这一点至关重要。在本文的后半部分中,特别是对虚拟析构函数的解释。如果析构函数必须始终声明为虚拟的那么,为什么声明一个非虚函数是合法的?我可以想到的一个原因是:如果你不使用多态性,那么析构函数作为虚拟变量会强制创建一个VTABLE(C++中,只有在一个类中有一个或多个虚拟方法时才创建VTHT)。C++允许程序员只根据需求激活多态性机制,因此如果不需要,则没有理由声明Dor Tor虚拟化。编译器知道是否派生出一个类,所以所有这些都可以是自动化的。只是我们坚持单独编译单元。这对编程活动有很高的成本。Victivity…析构函数和终结器具有不同的语义,因此这不是同一件事;)请参阅我的答案以获取其他参考。请标记其中一个答案。人们不会主动回答你的问题。析构函数和终结器有不同的语义,所以这不是一回事;)更多参考资料请参见我的答案。请在其中一个答案上标记。人们不会主动回答你的问题。我有`构造函数:基构造函数:派生析构函数:派生析构函数:基',我想你是指基*Var=new-Derived?我有`构造函数:基构造函数:派生析构函数:派生析构函数:基',我想你是指基*Var=new-Derived?