Читайте также:
|
|
The concept of boxing and unboxing is central to C#’s type system. It provides a bridge between value-types and reference-types by permitting any value of a value-type to be converted to and from type object. Boxing and unboxing enables a unified view of the type system wherein a value of any type can ultimately be treated as an object.
A boxing conversion permits a value-type to be implicitly converted to a reference-type.
Boxing a value of a non-nullable-value-type consists of allocating an object instance and copying the non-nullable-value-type value into that instance.
Boxing a value of a nullable-type produces a null reference if it is the null value (HasValue is false), or the result of unwrapping and boxing the underlying value otherwise.
The actual process of boxing a value of a non-nullable-value-type is best explained by imagining the existence of a generic boxing class, which behaves as if it were declared as follows:
sealed class Box<T>: System.ValueType
{
T value;
public Box(T t) {
value = t;
}
}
Boxing of a value v of type T now consists of executing the expression new Box<T>(v), and returning the resulting instance as a value of type object. Thus, the statements
int i = 123;
object box = i;
conceptually correspond to
int i = 123;
object box = new Box<int>(i);
A boxing class like Box<T> above doesn’t actually exist and the dynamic type of a boxed value isn’t actually a class type. Instead, a boxed value of type T has the dynamic type T, and a dynamic type check using the is operator can simply reference type T. For example,
int i = 123;
object box = i;
if (box is int) {
Console.Write("Box contains an int");
}
will output the string “Box contains an int” on the console.
A boxing conversion implies making a copy of the value being boxed. This is different from a conversion of a reference-type to type object, in which the value continues to reference the same instance and simply is regarded as the less derived type object.
An unboxing conversion permits a reference-type to be explicitly converted to a value-type.
An unboxing operation to a non-nullable-value-type consists of first checking that the object instance is a boxed value of the given non-nullable-value-type, and then copying the value out of the instance.
Unboxing to a nullable-type produces the null value of the nullable-type if the source operand is null, or the wrapped result of unboxing the object instance to the underlying type of the nullable-type otherwise.
Referring to the imaginary boxing class described in the previous section, an unboxing conversion of an object box to a value-type T consists of executing the expression ((Box<T>)box).value. Thus, the statements
object box = 123;
int i = (int)box;
conceptually correspond to
object box = new Box<int>(123);
int i = ((Box<int>)box).value;
For an unboxing conversion to a given non-nullable-value-type to succeed at run-time, the value of the source operand must be a reference to a boxed value of that non-nullable-value-type. If the source operand is null, a System.NullReferenceException is thrown. If the source operand is a reference to an incompatible object, a System.InvalidCastException is thrown.
For an unboxing conversion to a given nullable-type to succeed at run-time, the value of the source operand must be either null or a reference to a boxed value of the underlying non-nullable-value-type of the nullable-type. If the source operand is a reference to an incompatible object, a System.InvalidCastException is thrown.
Дата добавления: 2015-11-16; просмотров: 76 | Нарушение авторских прав
<== предыдущая страница | | | следующая страница ==> |
Автоматическое управление памятью ссылочных данных | | | Типы данных со значением null |