Używa instrukcji IL isinst
do wykonywania rzutowania zamiast instrukcji castclass
, która jest używana podczas rzutowania. Jest to specjalna instrukcja, która wykonuje rzut, jeśli jest ważna, inaczej pozostawia na stosie null
, jeśli nie jest. Więc nie, to nie tylko tłumi wyjątek, i jest o rząd wielkości szybszy niż to robi.
pamiętać, że istnieją pewne różnice w zachowaniu między instrukcją isinst
i castclass
- z których głównym jest, że isinst
nie uwzględnia operatorów odlewanych zdefiniowanych przez użytkownika, to tylko uważa hierarchii dziedziczenia, na przykład bezpośrednie jeśli zdefiniować następujące dwie klasy bez hierarchii dziedziczenia, ale wyraźnego operatora Obsada:
class A
{
public int Foo;
}
class B
{
public int Foo;
public static explicit operator B(A a)
{
return new B { Foo = a.Foo };
}
}
Następnie dodaje się uda:
var a = new A { Foo = 3 };
var b = (B)a;
Console.WriteLine(b.Foo); // prints 3
Jednak następujące nie kompilacji z błędem „nie można przekonwertować Typ „a” do „B” poprzez konwersję odniesienia, boks konwersji, unboxing nawrócenia, przemiany pakowy lub null konwersji typu”
var a = new A { Foo = 3 };
var b = a as B;
Więc jeśli masz y skonfigurowane przez użytkownika konfiguracje rzutowania (które zazwyczaj są złym pomysłem na typy odniesienia, z tego i innych powodów), powinieneś być świadomy tej różnicy.
Jaki jest powód, dla którego nie zostanie skompilowany? Myślałem, że "as" jest oceniane tylko podczas wykonywania kodu? Czy to oznacza, że kompilator sprawdza również przesyłanie podczas kompilacji? – faulty
@faulty - kompilator statycznie sprawdza rzuty, jeśli to możliwe, aby upewnić się, że nie piszesz kodu, który nie może się powieść (nie pamiętam, czy było to ostrzeżenie lub błąd, ponieważ zawsze mam ostrzeżenia, gdy błędy są włączone). –