2012-03-26 10 views
10

Supongamos que tengo un IEnumerable<int> y quiero que estos se conviertan en sus caracteres equivalentes ASCII.IEnumerable.Cast() vs fundición en IEnumerable.Select()

Para un entero simple, sería simplemente (char)i, por lo que siempre hay collection.Select(i => (char)i), pero pensé que sería un poco más limpio usar collection.Cast().

¿Alguien puede explicar por qué obtengo un InvalidCastException cuando uso collection.Cast<char>() pero no con collection.Select(i => (char)i)?

Editar: Curiosamente, cuando llamo al collection.OfType<char>() me sale un juego vacío.

Respuesta

10

Los métodos Cast<T> y OfType<T> solo realizan conversiones de referencia y de unboxing. Entonces no pueden convertir un tipo de valor a otro tipo de valor.

Los métodos operan en la interfaz no genérica IEnumerable, por lo que esencialmente están convirtiendo de IEnumerable<object> a IEnumerable<T>. Por lo tanto, la razón por la que no puede usar Cast<T> para convertir de IEnumerable<int> a IEnumerable<char> es la misma razón por la que no puede convertir int en un char.

Esencialmente, Cast<char> en su ejemplo falla porque el siguiente falla:

object ascii = 65; 
char ch = (char)ascii; <- InvalidCastException 

Ver Jon Skeet de excelente EduLinq post para más detalles.

+0

Gracias! Un poco contra-intuitivo, pero tiene sentido – hehewaffles

+0

El enlace al blog de Jon Skeet parece estar roto. Aquí hay una alternativa: http://edulinq.googlecode.com/hg/posts/33-CastAndOfType.html –

+0

@TylerGill, este enlace también está roto – 3per