Casting: (NewType) vs. Object como NewType

votos
79

Posible duplicado:
conversión versus uso de la palabra clave 'como' en el CLR

¿Cuál es en realidad la diferencia entre estos dos moldes?

SomeClass sc = (SomeClass)SomeObject;
SomeClass sc2 = SomeObject as SomeClass;

Normalmente, ambos deberían ser moldes explícitos para el tipo especificado?

Publicado el 05/08/2008 a las 16:42
fuente por usuario
En otros idiomas...                            


13 respuestas

votos
82

El primero emitirá una excepción si el tipo de fuente no se puede convertir al tipo de destino. Esto último dará como resultado que sc2 sea una referencia nula, pero no una excepción.

[Editar]

Mi respuesta original es sin duda la diferencia más pronunciada, pero, como señala Eric Lippert , no es la única. Otras diferencias incluyen:

  • No puede usar el operador 'as' para convertir a un tipo que no acepte 'nulo' como un valor
  • No puede usar 'como' para convertir cosas, como los números en una representación diferente (float to int, por ejemplo).

Y, finalmente, al utilizar 'como' frente al operador de reparto, también dices "No estoy seguro de si esto tendrá éxito".

Respondida el 05/08/2008 a las 16:44
fuente por usuario

votos
27

También tenga en cuenta que solo puede usar la palabra clave as como tipo de referencia o tipo anulable

es decir:

double d = 5.34;
int i = d as int;

no compilará

double d = 5.34;
int i = (int)d;

compilará

Respondida el 05/08/2008 a las 17:15
fuente por usuario

votos
9

La conversión de tipo con "como" es, por supuesto, mucho más rápida cuando falla el lanzamiento, ya que evita el gasto de lanzar una excepción.

Pero no es más rápido cuando el elenco tiene éxito. El gráfico en http://www.codeproject.com/KB/cs/csharpcasts.aspx es engañoso porque no explica lo que está midiendo.

La conclusión es:

  • Si espera que el lanzamiento tenga éxito (es decir, una falla sería excepcional), use un molde.

  • Si no sabe si tendrá éxito, use el operador "as" y pruebe el resultado para nulo.

Respondida el 16/09/2008 a las 20:21
fuente por usuario

votos
5

Una diferencia entre los dos enfoques es que el primero ((SomeClass) obj) puede provocar la llamada de un convertidor de tipo .

Respondida el 08/11/2008 a las 00:46
fuente por usuario

votos
4

Así el 'como' operador "ayuda" enterrar su problema de manera más bajo porque cuando se proporciona una instancia incompatibles se devolverá un valor nulo, tal vez usted que pasará a un método que pasarlo a otro y así sucesivamente y, finalmente,' ll obtener una NullReferenceException que harán de su depuración más difícil.

No abusar de ella. El operador de conversión directa es mejor en el 99% de los casos.

Respondida el 28/10/2010 a las 10:21
fuente por usuario

votos
4

Aquí hay una buena manera de recordar el proceso que cada uno de ellos sigue y que uso cuando trato de decidir cuál es mejor para mi circunstancia.

DateTime i = (DateTime)value;
// is like doing
DateTime i = value is DateTime ? value as DateTime : throw new Exception(...);

y el siguiente debería ser fácil de adivinar qué hace

DateTime i = value as DateTime;

en el primer caso, si no se puede emitir el valor que arroja una excepción en el segundo caso, si el valor no se puede convertir, i se establece en nulo.

Por lo tanto, en el primer caso se realiza una detención estricta si el yeso falla en el segundo lanzamiento, luego se realiza una detención suave y es posible que se encuentre con una NullReferenceException más adelante.

Respondida el 05/08/2008 a las 18:46
fuente por usuario

votos
3

Para ampliar el comentario de Rytmis , no puede usar la palabra clave as para estructuras (tipos de valores), ya que no tienen valor nulo.

Respondida el 07/09/2008 a las 09:08
fuente por usuario

votos
2

Todo esto se aplica a los tipos de referencia, los tipos de valores no pueden usar la aspalabra clave ya que no pueden ser nulos.

//if I know that SomeObject is an instance of SomeClass
SomeClass sc = (SomeClass) someObject;


//if SomeObject *might* be SomeClass
SomeClass sc2 = someObject as SomeClass;

La sintaxis de conversión es más rápida, pero solo cuando tiene éxito, es mucho más lento para fallar.

La mejor práctica es usarla ascuando no se conoce el tipo:

//we need to know what someObject is
SomeClass sc;
SomeOtherClass soc;

//use as to find the right type
if( ( sc = someObject as SomeClass ) != null ) 
{
    //do something with sc
}
else if ( ( soc = someObject as SomeOtherClass ) != null ) 
{
    //do something with soc
}

Sin embargo, si está absolutamente seguro de que someObjectes una instancia de, SomeClassentonces use cast.

En .Net 2 o superior genéricos significa que muy rara vez necesita tener una instancia no tipada de una clase de referencia, por lo que este último se utiliza con menos frecuencia.

Respondida el 18/09/2008 a las 12:10
fuente por usuario

votos
1

Y para completar, Eric Lippert tiene una publicación en el blog sobre la diferencia y algunas advertencias.

Respondida el 09/10/2009 a las 01:04
fuente por usuario

votos
1

Para aquellos de ustedes con experiencia en VB.NET, (tipo) es lo mismo que DirectCast y "como tipo" es lo mismo que TryCast.

Respondida el 16/09/2008 a las 22:55
fuente por usuario

votos
1

Es como la diferencia entre Parse y TryParse. Usas TryParse cuando esperas que pueda fallar, pero cuando tienes una gran seguridad de que no fallará, usas Parse.

Respondida el 08/08/2008 a las 13:00
fuente por usuario

votos
1

Lanzarán diferentes excepciones.
(): NullReferenceException
como: InvalidCastException,
que podría ayudar a la depuración.

La palabra clave "como" intenta lanzar el objeto y si el molde falla, null se devuelve en silencio. El operador de conversión lanzará una excepción de inmediato si el lanzamiento falla.

"Solo use la palabra clave C #" como "donde espera que el lanzamiento falle en un caso no excepcional. Si está contando con un elenco para tener éxito y no está preparado para recibir cualquier objeto que fallaría, debería usar el () operador de reparto para que se produzca una excepción apropiada y útil ".

Para ejemplos de código y una explicación adicional: http://blog.nerdbank.net/2008/06/when-not-to-use-c-keyword.html

Respondida el 05/08/2008 a las 16:49
fuente por usuario

votos
1

El lanzamiento entre paréntesis arroja una excepción si el intento de lanzamiento falla. El lanzamiento "como" devuelve nulo si falla el intento de lanzamiento.

Respondida el 05/08/2008 a las 16:45
fuente por usuario

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more