"Hej, Amigo! Emnet for dagens lektion er udvidelse og indsnævring af typekonverteringer. Du har lært om udvidelse og indsnævring af primitive typer for længe siden. På niveau 10. I dag skal vi tale om, hvordan det fungerer for referencetyper, dvs. forekomster af klasser."

Faktisk er det hele ret simpelt. Forestil dig en klasses arvekæde: klassen, dens forælder, forælderens forælder osv., helt tilbage til Object-klassen. Fordi en klasse indeholder alle medlemsmetoder i den klasse, den nedarver , kan en forekomst af klassen gemmes i en variabel , hvis type er en hvilken som helst af dens forældre.

Her er et eksempel:

Kode Beskrivelse
class Animal
{
public void doAnimalActions();
}class Cat extends Animal
{
public void doCatActions();
}class Tiger extends Cat
{
public void doTigerActions();
}
Her har vi tre klasseerklæringer: Dyr, Kat og Tiger. Kat arver dyr. Og Tiger arver kat.
public static void main(String[] args)
{
Tiger tiger = new Tiger();
Cat cat = new Tiger();
Animal animal = new Tiger();
Object obj = new Tiger();
}
Et Tiger-objekt kan altid tildeles en variabel, hvis type er en af ​​dens forfædres type. For Tiger-klassen er disse Kat, Dyr og Objekt.

Lad os nu tage et kig på udvidelse og indsnævring af konverteringer.

Hvis en tildelingsoperation får os til at bevæge os opad i arvekæden (mod klassen Object), så har vi at gøre med en udvidende konvertering (også kendt som upcasting). Hvis vi bevæger os ned i kæden mod objektets type, så er det en indsnævrende konvertering (også kendt som downcasting).

At rykke op i arvekæden kaldes udvidelse, fordi det fører til en mere generel type. Men ved at gøre det mister vi evnen til at påberåbe de metoder, der er tilføjet klassen gennem arv.

Kode Beskrivelse
public static void main(String[] args)
{
Object obj = new Tiger();
Animal animal = (Animal) obj;
Cat cat = (Cat) obj;
Tiger tiger = (Tiger) animal;
Tiger tiger2 = (Tiger) cat;
}
Når du indsnævrer typen, skal du bruge en typekonverteringsoperator, dvs. vi udfører en eksplicit konvertering.

Dette får Java-maskinen til at kontrollere, om objektet virkelig arver den type, vi ønsker at konvertere det til.

Denne lille innovation producerede en mangfoldig reduktion i antallet af typestøbefejl og øgede stabiliteten af ​​Java-programmer betydeligt.

Kode Beskrivelse
public static void main(String[] args)
{
Object obj = new Tiger();
if (obj instanceof Cat)
{
Cat cat = (Cat) obj;
cat.doCatActions();
}}
Endnu bedre, brug en  instans af check
public static void main(String[] args)
{
Animal animal = new Tiger();
doAllAction(animal);

Animal animal2 = new Cat();
doAllAction(animal2);

Animal animal3 = new Animal();
doAllAction(animal3);
}

public static void doAllAction(Animal animal)
{
if (animal instanceof Tiger)
{
Tiger tiger = (Tiger) animal;
tiger.doTigerActions();
}

if (animal instanceof Cat)
{
Cat cat = (Cat) animal;
cat.doCatActions();
}

animal.doAnimalActions();
}
Og her er hvorfor. Tag et kig på eksemplet til venstre.

Vi (vores kode) ved ikke altid, hvilken type objekt vi arbejder med. Det kan være et objekt af samme type som variablen (Animal), eller en hvilken som helst efterkommertype (Cat, Tiger).

Overvej doAllAction-metoden. Det fungerer korrekt, uanset hvilken type objekt der sendes ind.

Med andre ord fungerer det korrekt for alle tre typer: Dyr, Kat og Tiger.

public static void main(String[] args)
{
Cat cat = new Tiger();
Animal animal = cat;
Object obj = cat;
}
Her har vi tre opgaveoperationer. De er alle eksempler på udvidede konverteringer.

Typestøbningsoperatøren er ikke nødvendig her, fordi ingen kontrol er nødvendig. En objektreference kan altid gemmes i en variabel, hvis type er en af ​​dens forfædre.

"Åh, det næstsidste eksempel gjorde alt klart: hvorfor kontrollen er nødvendig, og hvorfor typestøbning er nødvendig."

"Jeg håber det. Jeg vil gerne henlede din opmærksomhed på dette faktum:"

Intet af dette får et objekt til at ændre sig på nogen måde! Det eneste, der ændrer sig, er antallet af tilgængelige metoder til at blive kaldt på en bestemt referencevariabel.

For eksempel lader en Cat-variabel dig kalde metoderne doAnimalActions og doCatActions. Den ved ikke noget om doTigerActions-metoden, selvom den peger på et Tiger-objekt.

"Ja, jeg forstår det. Det var nemmere, end jeg troede, det ville være."