C# casting to nullable type?

.net-4.0, c#, casting, clr

Solution

In your first example, the `as` operator attempts to use the object `s` as an `int?`. Since `int?` isn't anywhere in the inheritance chain of `short?`, this operation fails.

In your second example, you're actually creating a new `int? i` with the value from `short? s`. This is a more generous operation, because it doesn't have to preserve the original `s` object on the left hand side.

The important point here is that `as` isn't allowed to do anything that doesn't preserve your object's identity. An explicit cast can.

Here's what the C# standard says about how the `(int?)` form works:

6.1.4 Implicit nullable conversions

Predefined implicit conversions that operate on non-nullable value types can also be used with nullable forms of those types. For each of the predefined implicit identity and numeric conversions that convert from a non-nullable value type S to a non-nullable value type T, the following implicit nullable conversions exist:

· An implicit conversion from S? to T?.

· An implicit conversion from S to T?.

Evaluation of an implicit nullable conversion based on an underlying conversion from S to T proceeds as follows:

· If the nullable conversion is from S? to T?:

o If the source value is null (HasValue property is false), the result is the null value of type T?.

o Otherwise, the conversion is evaluated as an unwrapping from S? to S, followed by the underlying conversion from S to T, followed by a wrapping (§4.1.10) from T to T?.

· If the nullable conversion is from S to T?, the conversion is evaluated as the underlying conversion from S to T followed by a wrapping from T to T?.

Problem

Beyond the regular boring difference between `Cast` and `As` - if i know that apple is a Fruit so I can use `(Fruit)apple` - and it throws an exception if it aint - `as value` can be checked against null to see if succeeded [won't throw Exception...] However Ive been reading @EricLippert article about this and there was a nice sample about Nullable Value Types : ``` short? s = (short?)123; int? i = s as int?; ``` this won't compile... Cannot convert type 'short?' to 'int?' via a reference conversion, boxing conversion, unboxing conversion, wrapping conversion, or null type conversion Fine. so why this : ``` short? s = (short?)123; int? i = (int?)s; ``` Does Compile ? ( Against ALL Expectations ! I KNOW that `s` is not `int?` - and it should go BANG but it aint ...) the Cast checking here should be much more deadly than the former example (which went Bang) I feel bad asking about this much-talked subject. Thanks in Advance.

Original source