¿Hay algún tipo de penalización, por lo que solo debe establecerlos como anulables cuando realmente lo necesite?¿Cuál es la razón por la que no todos los tipos de valores son anulables?
Gracias
¿Hay algún tipo de penalización, por lo que solo debe establecerlos como anulables cuando realmente lo necesite?¿Cuál es la razón por la que no todos los tipos de valores son anulables?
Gracias
varias razones:
Nullable<T>
no existía hasta .NET 2.0, y no puede romper el código existente - especialmente con las diferentes reglas de boxeo para Nullable<T>
int
, puede ser que no quieren que sea anulable ... yo quiero que sea un int
, y yo no quiero tener que el registro de entrada de la manija/nulosbyte[]
, y ahora considere si se pudo anular byte
- mucha sobrecarga adicional; * Más que dejaría de hacer que blits etc *Rendimiento: Nullable<T>
añade un montón de sanciones adicionales; en particular, muchas llamadas ocultas a .HasValue
y .Value
/.GetValueOrDefault()
; esto se muestra en particular en los "operadores levantadas" - es decir x + y
se convierte en algo parecido a continuación, que se suma a los bucles apretados etc:
(x.HasValue && y.HasValue) ? (x.GetValueOrDefault() + y.GetValueOrDefault()) : null
Del mismo modo, x == y
que verificar:
==
en GetValueOrDefault()
de cadaun montón de gastos generales ....
tipos cuyo valor anulable son en realidad? No conozco ninguno.
EDITAR: Si se refiere al tipo de cadena, entonces no es un tipo de valor, sino un tipo de referencia.
Necesita envolverlos en el tipo Nullable
Pero eso es algo diferente. Creo que el tema principal significa que los tipos de valor se pueden anular de manera inmediata, probablemente haciendo referencia al tipo de cadena. – User
Creo que el OP significa algo así como "si los tipos de valores se pueden convertir en nulos, ¿por qué no se pueden anular desde el principio?". – Guffa
Sí, hay una penalización. La estructura Nullable<T>
contiene el valor y también un indicador booleano que determina la nulidad del valor.
Aunque el valor booleano es de solo un byte, las estructuras se alinean incluso con los límites de las palabras. Un int
utiliza cuatro bytes de memoria, pero un int?
necesita ocho bytes.
La pena es mucho peor que una palabra adicional. El diseño de la estructura que admite nulos significa que la creación de un 'Nullable
Además de respuesta Marc Gravell, compruebe el código reflejado desde anulable <T>:
public struct Nullable<T> where T: struct
{
private bool hasValue;
internal T value;
public Nullable(T value)
{
this.value = value;
this.hasValue = true;
}
public bool HasValue
{
get
{
return this.hasValue;
}
}
public T Value
{
get
{
if (!this.HasValue)
{
ThrowHelper.ThrowInvalidOperationException(ExceptionResource.InvalidOperation_NoValue);
}
return this.value;
}
}
public T GetValueOrDefault()
{
return this.value;
}
public T GetValueOrDefault(T defaultValue)
{
if (!this.HasValue)
{
return defaultValue;
}
return this.value;
}
public override bool Equals(object other)
{
if (!this.HasValue)
{
return (other == null);
}
if (other == null)
{
return false;
}
return this.value.Equals(other);
}
public override int GetHashCode()
{
if (!this.HasValue)
{
return 0;
}
return this.value.GetHashCode();
}
public override string ToString()
{
if (!this.HasValue)
{
return "";
}
return this.value.ToString();
}
public static implicit operator T?(T value)
{
return new T?(value);
}
public static explicit operator T(T? value)
{
return value.Value;
}
}
Usted' Notaremos la existencia del booleano HasValue
y cómo las propiedades lo usan.
Considere la implementación.Un número entero en C# se define como
public struct Int32 : IComparable, IFormattable, IConvertible, IComparable<int>, IEquatable<int>
A struct se almacena directamente en la pila, en contraposición a los objetos referencias que son punteros a la memoria (la referencia en sí está en la pila, pero la asignación está en la pila) .
Una referencia NULL simplemente significa que el puntero en la pila no se ha inicializado a una ubicación en el montón.
¿No te olvidas del extra? operador que lanzaron también. int i = j ?? k; // si j es nulo, use k. –
bueno, eso no es específico de 'Nullable' - pero otro buen punto –
@Chris ¿funciona eso en absoluto? j no puede ser nulo, de lo contrario no puede asignarlo a un tipo de valor, ¿verdad? ;-) –