2009-12-10 27 views
87

En C#, cuando lo haceC# constructor orden de ejecución

Class(Type param1, Type param2) : base(param1) 

es el constructor de la clase ejecuta en primer lugar, y luego el constructor de la superclase se llama o se llama al constructor de base en primer lugar?

+1

tengo nunca usé XNA, pero estoy fallando en ver una pregunta en tu ... pregunta. –

+4

¿Eso es todo? ¿Eso es todo lo que nos estás dando para seguir? Vamos, danos una pista ... animal, vegetal, mineral? –

+1

Presioné el botón demasiado rápido xD ... Lo siento, todavía estaba escribiendo ... – webdreamer

Respuesta

124

El orden es:

  • variables de miembro se inicializan a los valores por defecto para todas las clases de la jerarquía

a continuación, comenzando con la clase más derivada:

  • inicializadores de variables se ejecutan para el tipo más derivada
  • Constructor encadenamiento funciona el que se va a ser llamado
  • se inicializa La clase base (recurse todo esto :)
  • Los cuerpos de constructor en el constructor de la clase de base la cadena en esta clase son ejecutados (tenga en cuenta que no puede haber más de una si están encadenados con Foo() : this(...) etc

Tenga en cuenta que en Java, la clase base es inicializado antes inicializadores de variables se ejecutan. Si alguna vez transfiere un código, esta es una diferencia importante que debe saber :)

Tengo un page with more details si está interesado.

+4

Parece que la mitad de mis contribuciones aquí están apuntando a sus respuestas; pero Eric Lippert también escribió un buen par de publicaciones sobre este tema: http://blogs.msdn.com/ericlippert/archive/2008/02/15/why-do-initializers-run-in-the-opposite- order-as-constructors-part-one.aspx http://blogs.msdn.com/ericlippert/archive/2008/02/18/why-do-initializers-run-in-the-opposite-order-as- constructors-part-two.aspx –

+0

Incluyendo los efectos de los inicializadores de recopilación, un poco más en profundidad que la pregunta tal vez, pero una buena lectura. –

+0

+1 para la comparación con Java. Además, creo que ese es el caso de C++, pero no estoy 100% seguro. –

41

Llamará primero al constructor base. También tenga en cuenta que si no coloca el :base(param1) después de su constructor, se llamará al constructor vacío de la base.

10

El constructor de la clase base se llama primero.

0

Su pregunta es un poco confuso, pero estoy suponiendo que significaba para hacer la siguiente

Cuándo llamo al constructor base para mi objeto XNA vs utilizando el constructor por defecto impilict

La respuesta a esto depende en gran medida tanto de su escenario como del objeto subyacente. Podría aclarar un poco el ingenio la siguiente

  • Cuál es el escenario
  • ¿Cuál es el tipo de objeto de base de TerrainCollision?

Mi mejor respuesta es que, en el caso de que tenga parámetros que se alineen con los parámetros del constructor de la clase base, seguramente debería llamarlo.

1

[Editar: en el tiempo que me llevó responder, la pregunta había cambiado por completo].

La respuesta es que llama primero a la base.

[Respuesta original a la vieja pregunta de abajo]

lo preguntas cuando se haría la "base" de bits de la llamada al constructor?

Si es así, sería "cadena" una llamada a la base si el constructor de clase se deriva de otra clase que tiene este constructor:

public class CollisionBase 
    { 
     public CollisionBase(Body body, GameObject entity) 
     { 

     } 
    } 

    public class TerrainCollision : CollisionBase 
    { 
     public TerrainCollision(Body body, GameObject entity) 
      : base(body, entity) 
     { 

     } 
    } 

En este ejemplo, TerrainCollision deriva de CollisionBase.Por el encadenamiento de los constructores de esta manera, se asegura el constructor especificado se pidió a la clase base con los parámetros suministrados, en lugar del constructor por defecto (si es que existe en la base)

0

El mecanismo del constructor es mucho mejor, ya que deja la aplicación para utilizar el encadenamiento de constructores y, si extendiera la aplicación, permite por herencia la capacidad de realizar cambios mínimos de código. Jon Skeets Article

6

No estoy seguro si esto debería ser un comentario/respuesta, pero para los que aprenden con el ejemplo de este violín ilustra el orden así: https://dotnetfiddle.net/kETPKP

using System; 

// order is approximately 
/* 
    1) most derived initializers first. 
    2) most base constructors first (or top-level in constructor-stack first.) 
*/ 
public class Program 
{ 
    public static void Main() 
    { 
     var d = new D(); 
    } 
} 

public class A 
{ 
    public readonly C ac = new C("A"); 

    public A() 
    { 
     Console.WriteLine("A"); 
    } 
    public A(string x) : this() 
    { 
     Console.WriteLine("A got " + x); 
    } 
} 

public class B : A 
{ 
    public readonly C bc = new C("B"); 

    public B(): base() 
    { 
     Console.WriteLine("B"); 
    } 
    public B(string x): base(x) 
    { 
     Console.WriteLine("B got " + x); 
    } 
} 

public class D : B 
{ 
    public readonly C dc = new C("D"); 

    public D(): this("ha") 
    { 
     Console.WriteLine("D"); 
    } 
    public D(string x) : base(x) 
    { 
     Console.WriteLine("D got " + x); 
    } 
} 

public class C 
{ 
    public C(string caller) 
    { 
     Console.WriteLine(caller + "'s C."); 
    } 
} 

Resultado:

D's C. 
B's C. 
A's C. 
A 
A got ha 
B got ha 
D got ha 
D 
Cuestiones relacionadas