Cast<int>.Cast<int?> applied on generic enum collection results in invalid cast exception

c#, casting, enums, type-conversion

Solution

Ok I have come to find out the cause, which is still strange. I should have checked up `Cast<T>` implementation myself first of all!

This is how `Cast<T>` is implemented:

public static IEnumerable<TResult> Cast<TResult>(this IEnumerable source)
{
    IEnumerable<TResult> enumerable = source as IEnumerable<TResult>;
    if (enumerable != null)
    {
        return enumerable; // this is the culprit..
    }
    if (source == null)
    {
        throw Error.ArgumentNull("source");
    }
    return Enumerable.CastIterator<TResult>(source);
}

private static IEnumerable<TResult> CastIterator<TResult>(IEnumerable source)
{
    foreach (object current in source)
    {
        yield return (TResult)((object)current);
    }
    yield break;
}

Now the problem is with the first `Cast<int>` call:

new[] { Gender.Male }.Cast<int>()

Here `source as IEnumerable<TResult>` where `source` is `new[] { Gender.Male }` and `TResult` is `int` in the generic method returns a non null value (which basically means (`new[] { Gender.Male }` is an `IEnumerable<int>` in generic context), and hence it returns the same enumerable back which is `Gender[]`, and in the next `Cast<int?>` call, the actual cast is performed, which is from `Gender` to `int?` which fails. As to why this happens in generic context, catch it in this question.

Problem

``` enum Gender { Male, Female } var k = new[] { Gender.Male }.Cast<int>().ToList().Cast<int?>().ToList(); //alright var p = new[] { Gender.Male }.Cast<int>().Cast<int?>().ToList(); //InvalidCastException ``` What is the cause for the second case? I know I cant cast a boxed `enum` to `int?` directly, but I do a two stage casting, ie `Cast<int>.Cast<int?>` which should be working. Edit: This is surprising considering the below works: ``` object o = Gender.Male; int i = (int)o; // so here the cast is not to an entirely different type, which works ```

Original source

Related problems