C#中的基本构造函数-首先调用哪个?

时间:2020-03-06 14:47:36  来源:igfitidea点击:

哪个首先被称为基本构造函数或者"此处的其他内容"?

public class MyExceptionClass : Exception
{
    public MyExceptionClass(string message, string extrainfo) : base(message)
    {
        //other stuff here
    }
}

解决方案

我说基地

编辑请参阅:

http://www.c-sharpcorner.com/UploadFile/rajeshvs/ConsNDestructorsInCS11122005010300AM/ConsNDestructorsInCS.aspx

那里说:

using System;
class Base
{

public Base()
{
    Console.WriteLine("BASE 1");
}
public Base(int x)
{
    Console.WriteLine("BASE 2");
}
}

class Derived : Base
{
public Derived():base(10)
{
    Console.WriteLine("DERIVED CLASS");
}
}

class MyClient
{
public static void Main()
{
    Derived d1 = new Derived();
}
}
This program outputs 
  
  BASE2 
  
  DERIVED CLASS

基本构造函数将首先被调用。

试试吧:

public class MyBase
{
  public MyBase()
  {
    Console.WriteLine("MyBase");
  }
}

public class MyDerived : MyBase
{
  public MyDerived():base()
  {
    Console.WriteLine("MyDerived");
  }
}

http://www.devhood.com/tutorials/tutorial_details.aspx?tutorial_id=777

首先调用基础构造函数。

将调用Exception构造函数,然后将调用Child类构造函数。

简单的OO原理

在这里看看
http://www.dotnet-news.com/lien.aspx?ID=35151

实际上,派生类构造函数首先执行,但是Ccompiler插入对基类构造函数的调用,作为派生构造函数的第一条语句。

因此:首先执行了派生,但是"看起来"首先执行了基础。

基类构造函数在派生类构造函数之前被调用,但是派生类构造函数在基类初始化构造函数之前被调用。例如。在以下代码中:

public class BaseClass {

    private string sentenceOne = null;  // A

    public BaseClass() {
        sentenceOne = "The quick brown fox";  // B
    }
}

public class SubClass : BaseClass {

    private string sentenceTwo = null; // C

    public SubClass() {
        sentenceTwo = "jumps over the lazy dog"; // D
    }
}

执行顺序为:C,A,B,D。

查看以下2条msdn文章:

  • 为什么初始化程序与构造函数的运行顺序相反?第一部分
  • 为什么初始化程序与构造函数的运行顺序相反?第二部分

首先将调用基本构造函数,否则,在"其他内容"必须使用由基本构造函数初始化的成员变量的情况下,我们将得到编译时错误,因为类成员尚未初始化。

在子构造函数中完成任何工作之前,将调用base(?)。

即使不使用:base()也是如此(在这种情况下,将调用0参数的基本构造函数。)

它的工作原理类似于Java,

public Child()
{
   super(); // this line is always the first line in a child constructor even if you don't put it there! ***
}

***例外:我可以改用super(1,2,3)。但是,如果我没有显式调用super,则会调用super()。

正如其他人所说,基本构造函数首先被调用。但是,构造函数并不是真正发生的第一件事。

假设我们有这样的课程:

class A {}

class B : A {}

class C : B {}

首先,将按从最高派生到最低派生的类的顺序调用字段初始化器。因此,首先是C的字段初始值设定项,然后是B的初始值设定项,然后是A的初始值。

然后将以相反的顺序调用这些构造函数:首先是A的构造函数,然后是B,然后是C。

构造函数调用从下往上调用(激发),并从上到下执行。因此,如果我们有从C类继承而来的C类,而B类又继承了A类,则在创建C类的实例时,将调用C的构造函数,从而依次调用B的讲师,而B的构造函数又将调用B的构造函数。 A.现在执行A的构造函数,然后执行B的构造函数,然后执行C的构造函数。

不要试图记住它,而是要向自己解释发生了什么。假设我们有一个名为Animal的基类和一个名为Dog的派生类。派生类为基类添加了一些功能。因此,在执行派生类的构造函数时,基类实例必须可用(以便可以向其添加新功能)。这就是为什么构造函数从基础执行到派生,而析构函数以相反的方式执行的原因,首先是派生的析构函数,然后是基础析构函数。

(这已简化,但是它可以将来无需实际记住此问题即可回答此问题。)

埃里克·利珀特(Eric Lippert)在对象初始化的相关问题上发表了一篇有趣的文章,其中解释了构造函数和字段初始化程序排序的原因:

为什么初始化程序以相反的顺序作为构造函数运行?第一部分
为什么初始化程序以相反的顺序作为构造函数运行?第二部分