2011-01-31 16 views
6

Parece que no hay sintaxis de lenguaje para especificar tanto un constructor this() como un constructor base(). Dado el siguiente código:constructores this() y base() en C#

public class Bar : Foo 
{ 
    public Bar() 
     :base(1) 
     //:this(0) 
    { } 
    public Bar(int schmalue) 
     :Foo(1) 
    { 
     //Gobs of initialization code 
     ... 
     Schmalue = schmalue; 
    } 

    public int Schmalue { get; private set; } 
} 

public class Foo 
{ 
    public Foo() 
    { 
     Value = 0; 
    } 

    public class Foo(int value) 
    { 
     Value = value; 
    } 

    public int Value { get; private set; } 
} 

El compilador me da un error que indica que '{' se esperaba cuando el descomentando: esto (0) llamada. Esto es molesto porque me causa factorizar mi código en un método privado, cuando esta funcionalidad se proporcionó claramente para evitar tal cosa.

¿Simplemente estoy haciendo esto mal? No intenté separador, punto y coma, coma ... Parece que esto fue solo un descuido del equipo de desarrollo. Me interesa saber por qué se omitió esto, si estoy haciendo esto de la manera incorrecta o si alguien tiene buenas sugerencias para las alternativas.

+1

posible duplicado de [Llamando al constructor anulado y al constructor base en C#] (http://stackoverflow.com/questions/335286/calling-overriden-constructor-and-base-constructor-in-c) – Oded

+2

Gracias por todo de la respuesta. En esencia, el problema es que esto() también puede llamar a otro constructor base. – Sprague

Respuesta

8

Esto se puede hacer mediante la invocación del constructor base al final de su cadena:

public Bar(): this(0) {} 
public Bar(int schmalue): base(1) { 
    // ... initialize 
} 
+0

Gracias, esta es la respuesta. Muchos otros después de que usted declaró cosas similares (algunos más explícitamente) pero definitivamente es esto. – Sprague

3

No, solo se puede encadenar a un solo constructor, ya sea otro constructor en la misma clase o un constructor base.

No está muy claro lo que estás tratando de hacer. Normalmente encuentro que vale la pena crear un constructor "primario" en una clase derivada: todos los demás constructores dentro de la clase derivada usan "this" para llamar al primario, que llama a "base" para llamar al constructor base apropiado.

Mientras que el modelo no se ajusta a todos los escenario - en particular cuando se quiere llamar a diferentes constructores de base de diferentes constructores derivados - es generalmente un buen modelo.

1

En su diseño no puedo ver muchas cosas en común entre las clases Bar y Foo. ¿Por qué Foo deriva de Bar cuando vuelve a implementar todo? Ambas clases tienen una propiedad entera con getter público y setter privado y ambas clases tienen constructores por defecto y un constructor que permite inicializar la propiedad integer. Entonces, ¿por qué existen esas dos clases de todos modos?

0

El segundo ctor en Bar es simplemente errónea. Proveedores:

public Bar(int schmalue) 
    :base(1) //would call Foo(1) 
{ 
    //Gobs of initialization code 
    ... 
    Schmalue = schmalue; 
} 

El comentario en el primer ctor parece significar algo así como

  • barra de inicialización con schmalue = 0

  • llamada ctor base de Foo con el valor = 1

¿No?

Para ello, vuelva a colocar la segunda ctor y simplemente añadir otro ctor (privada) que puede manejar ambos valores

public Bar(int schmalue) 
    :this(1, schmalue) //would call Bar(1, schmalue) 
{ 
} 

private Bar(int value, int schmalue) 
:base(value) 
{ 
    //Gobs of initialization code 
    ... 
    Schmalue = schmalue; 
} 
3

Considérese lo que sucedería si se puede llamar tanto this y base como constructores de un constructor. Supongamos que primero se llamaría al constructor base. Luego, se llamará al constructor this, que a su vez llamará al constructor base. Por lo tanto, la clase base se instanciaría dos veces. Esto rompe la semántica de los constructores, es decir, que un objeto se construye una vez.

Como tal, llamando a base y this está prohibido. Deje que su constructor delegado this llame a la base con parámetros específicos, si es necesario.