Casting di tipo di errore e costruttore
-
01-10-2019 - |
Domanda
Ho due classi
public class A
{
public A()
{
}
}
public class B:A
{
public B()
{
}
}
ed il codice principale è il seguente
A oa = new B();
B ob = new A();
Qui linea 1 viene compilato correttamente, mentre la linea 2 visualizza l'errore typecasting. Perché questo accade. Che cosa succede esattamente quando new B()
e new A()
viene chiamato?
Soluzione
Che cosa succede esattamente quando nuovi B () e nuovo A () viene chiamato?
-
new A()
costruisce un oggetto di tipoA
sul mucchio e ritorna un riferimento ad esso. -
new B()
costruisce un oggetto di tipoB
sul mucchio e ritorna un riferimento ad esso.
Qui linea 1 compila con successo mentre la linea 2 visualizza typecasting errore. Perché questo accade.
Da sottoclassi B
A
, è valido per un riferimento di tipo A
per fare riferimento a un oggetto di tipo run-time B
. Dopo tutto, B
è semplicemente un "caso speciale" di A
.
Tuttavia, il contrario non è vero, perché non tutti possono essere considerati A
s B
s.
Anche se questa viene applicata da C # s ' sicura tipo di sistema, anche se non c'è incompatibilità 'reale', le ragioni di tali restrizioni sono naturali. Immaginate, per esempio, che B
dichiarata public int Foo {get; set;}
proprietà.
Come ci si aspetterebbe questo si comporti:
B ob = new A();
ob.Foo = 5;
Questa è chiaramente illogico: reale oggetto che il riferimento si riferisce non ha tale proprietà. Di conseguenza, il compilatore vieta tali costrutti.
Ora immaginate hai cambiato il codice per:
B b = (B)new A();
Qui, si indica al compilatore che l'oggetto creato, sarà, a run-time , sia assegnabile ad un riferimento di tipo B
. Questo compilerà bene, ma dal momento che l'affermazione è chiaramente errato, un InvalidCastException
run-time saranno gettati.
In sintesi, il tipo di sistema di C # 's (se si ignorano dynamic
e alcuni casi particolari) è sia static e sicura : non sarà successo in grado di trattare una concreta istanza di A
come se fosse di tipo B
.
Altri suggerimenti
Si hanno dichiarato una variabile di tipo B
, e poi ha tentato di assegnare un valore di tipo A
ad esso. È stato definito B
di essere una sorta di A
, ma ciò non significa che tutti i di A
sono B
di.
Pensate a come questo:
class Animal { }
class Dog : Animal { }
class Cat : Animal { }
Si può fare Animal rex = new Dog()
, perché tutti i cani sono animali, ma non Dog fido = new Animal()
, perché non tutti gli animali sono cani.