JavaRush /Blogue Java /Random-PT /Convertendo tipos de referência em Java
Sant9Iga
Nível 41

Convertendo tipos de referência em Java

Publicado no grupo Random-PT
Bom dia, cara Javarash. Comecei a receber perguntas sobre conversão de tipos de referência em Java. Para não recontar sempre a mesma coisa, resolvi escrever um pequeno artigo.

Primeiro, vamos ver que tipo é o casting.

A conversão de tipo (conversão de tipo) é a conversão de um valor de variável de um tipo em um valor de outro tipo. Vejamos um exemplo do que é e com que se come. Temos alguma hierarquia de classes ( veja a Figura 1 ). Aqui você pode ver todas as classes da hierarquia, quem herda quem e os métodos de cada classe. Imagem 1Há uma adução em expansão e uma contração. Vemos que a classe Caté descendente da classe Pet. Pet, por sua vez, é sucessor da classe Animal. Quando escrevemos:
Animal animalCat = new Cat();
Animal animalDog = new YorkshireTerrier();
Este é um elenco em expansão (ou implícito). Expandimos os links animalCate animalDog. Eles se referem a objetos Cate Dog. Com tal conversão, não podemos animalCat/animalDogchamar métodos através de um link que estão em Cat/Dog, mas que não estão em Animal. Uma conversão estreita (ou explícita) ocorre na direção oposta:
Animal animalCat = new Cat();
Animal animalDog = new YorkshireTerrier();
Cat cat =(Cat)animalCat;
YorkshireTerrier dog = (YorkshireTerrier) animalDog;
Indicamos claramente para qual tipo queremos lançar este objeto. MAS TENHA CUIDADO!!! Se você fizer assim:
Animal animalCat = new Cat();
YorkshireTerrier dog = (YorkshireTerrier) animalCat;
o compilador irá pular este código. Mas RunTimeisso vai jogar fora para você:
Exception in thread "main" java.lang.ClassCastException: Animals.Cat cannot be cast to Animals.YorkshireTerrier
RunTimevê que Catexistem YorkshireTerrierduas classes diferentes. Para evitar ClassCastException durante a conversão restrita, use instanceof.
Animal animalCat = new Cat();
if (animalCat instanceof YorkshireTerrier)
{
    YorkshireTerrier dog = (YorkshireTerrier) animalCat;
}
Se animalCatfor YorkshireTerrier, então a atribuição ocorrerá; caso contrário, nada acontecerá.

Agora, por que isso é necessário se perdemos métodos e podemos obter esses erros?

Vejamos o código que fiz de acordo com o diagrama da Fig. 1 . AulaAnimal
public abstract class Animal
{
    String name;
    int age;
    String nameOfClass = getClass().getSimpleName();
    public void eat(){
        System.out.println(nameOfClass + ": Omnomnom");
    }
    public void sleep(){
        System.out.println(nameOfClass + ": Z-z-z-z");
    }
}
Uma classe WildAnimalque herda deAnimal
public abstract class WildAnimal extends Animal
{
    public void steelChicken()
    {
        System.out.println(nameOfClass+": Muhaha,I stole a chicken!");
    }
}
Uma classe Petque herda deAnimal
public abstract class Pet extends Animal
{
    public void peeInTray(){
        System.out.println(nameOfClass + ": Master, I peed");
    }
}
Uma classe Foxque herda deWildAnimal
public class Fox extends WildAnimal
{
    public void eatColobok(){
        System.out.println(nameOfClass + ": I will eat you, Colobok");
    }
}
Uma classe Wolfque herda deWildAnimal
public class Wolf extends WildAnimal
{
    public void hawlAtTheMoon(){
        System.out.println(nameOfClass + ": Ouuuuu!!!Ouuuu!!!");
    }
}
Uma classe Catque herda dePet
public class Cat extends Pet
{
    public void sleepOnKeyboard(){
        System.out.println(nameOfClass + ": Master, stop working!!I wanna sleep on your keyboard");
    }
}
Uma classe YorkshireTerrierque herda dePet
public class YorkshireTerrier extends Pet
{
    public void bark(){
        System.out.println(nameOfClass + ": Meow!!! Meow!!!");
    }
}
Imagine a situação. Precisamos reunir todos os animais em uma lista, alimentá-los e depois colocá-los na cama. Isso é fácil de fazer se criarmos ArrayListanimais ( Animal). E então chamamos os métodos correspondentes para cada animal:
public class ZOO
{
    public static void main(String[] args)
    {
        List<Animal> allAnimals = new ArrayList<>();
        allAnimals.add(new Cat());
        allAnimals.add(new Wolf());
        allAnimals.add(new Fox());
        allAnimals.add(new YorkshireTerrier());
        for (Animal animal : allAnimals)
        {
            animal.eat();
            animal.sleep();
        }
    }
}
Não consigo animalchamar o método bark()ou sleepOnKeyboard(). Porque a folha allAnimalscontém um gato, um lobo, um yorick e uma raposa, mas eles estão reduzidos a Animal. E eles só possuem os métodos que estão no Animal. Isso é muito bom, porque se pudéssemos chamar todos os métodos, então por que precisamos de um lobo que durma no teclado ou de um yorick que roube galinhas? Obrigado pela sua atenção. Espero que este artigo seja útil para você. Críticas e comentários são bem-vindos)
Comentários
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION