En .NET, un tipo de valor (C # struct
) no puede tener un constructor sin parámetros. De acuerdo con esta publicación, esto es obligatorio según la especificación CLI. Lo que sucede es que para cada tipo de valor se crea un constructor predeterminado (¿el compilador?) Que inicializa todos los miembros a cero (o null
).
¿Por qué no está permitido definir un constructor predeterminado?
Un uso trivial es para números racionales:
public struct Rational {
private long numerator;
private long denominator;
public Rational(long num, long denom)
{ /* Todo: Find GCD etc. */ }
public Rational(long num)
{
numerator = num;
denominator = 1;
}
public Rational() // This is not allowed
{
numerator = 0;
denominator = 1;
}
}
Usando la versión actual de C #, un Rational predeterminado es el 0/0
que no es tan genial.
PD : ¿Los parámetros predeterminados ayudarán a resolver esto para C # 4.0 o se llamará al constructor predeterminado definido por CLR?
Jon Skeet respondió:
Para usar su ejemplo, ¿qué le gustaría que sucediera cuando alguien lo hizo:
Rational[] fractions = new Rational[1000];
¿Debería pasar por su constructor 1000 veces?
Claro que debería, por eso escribí el constructor predeterminado en primer lugar. El CLR debe usar el constructor de puesta a cero predeterminado cuando no se define un constructor predeterminado explícito; de esa manera solo paga por lo que usa. Entonces, si quiero un contenedor de 1000 s no predeterminados Rational
(y quiero optimizar las 1000 construcciones), List<Rational>
usaré una matriz en lugar de una matriz.
Esta razón, en mi opinión, no es lo suficientemente fuerte como para evitar la definición de un constructor predeterminado.
Rational()
invoca el ctor sin parámetros en lugar del Rational(long num=0, long denom=1)
.
new Rational()
invocará al constructor si existe, sin embargo, si no existe, new Rational()
será equivalente a default(Rational)
. En cualquier caso, se le recomienda utilizar la sintaxis default(Rational)
cuando desee el "valor cero" de su estructura (que es un número "malo" con su diseño propuesto de Rational
). El valor predeterminado para un tipo de valor T
es siempre default(T)
. Por new Rational[1000]
lo tanto , nunca invocará constructores de estructuras.
denominator - 1
dentro de la estructura, de modo que el valor predeterminado se convierta en 0/1
Then if I want a container of 1000 non-default Rationals (and want to optimize away the 1000 constructions) I will use a List<Rational> rather than an array.
¿Por qué esperarías que una matriz invoque un constructor diferente a una Lista para una estructura?