freeCodeCamp/guide/portuguese/java/inheritance/index.md

8.4 KiB

title localeTitle
Inheritance Herança

Herança

Herança Java refere-se à capacidade de uma classe Java de inherit as propriedades de alguma outra classe. Pense nisso como uma criança herdando propriedades de seus pais, o conceito é muito semelhante a isso. Na linguagem Java, também é chamado de extender uma classe. Algumas coisas simples para lembrar:

  • A classe que estende ou herda é chamada de subclasse
  • A classe que está sendo estendida ou herdada é chamada de superclasse

Assim, a herança dá ao Java a capacidade legal de reutilizar código ou compartilhar código entre classes!

Vamos descrevê-lo com o exemplo clássico de uma classe Vehicle e uma classe Car :

public class Vehicle { 
    public void start() { 
        // starting the engine 
    } 
 
    public void stop() { 
        // stopping the engine 
    } 
 } 
 
 public class Car extends Vehicle { 
    int numberOfSeats = 4; 
 
    public int getNumberOfSeats() { 
        return numberOfSeats; 
    } 
 } 

Aqui, podemos ver a classe Car herdando as propriedades da classe Vehicle . Portanto, não precisamos escrever o mesmo código para os métodos start() e stop() para Car , pois essas propriedades estão disponíveis em sua controladora ou superclasse. Portanto, objetos criados a partir da classe Car também terão essas propriedades!

Car tesla = new Car(); 
 
 tesla.start(); 
 
 tesla.stop(); 

:rocket: Executar código

Mas, a classe pai tem os métodos da criança? Não, não.

Portanto, sempre que você precisar compartilhar uma parte comum do código entre várias classes, é sempre bom ter uma classe pai e estender essa classe sempre que necessário! Reduz o número de linhas de código, torna o código modular e simplifica o teste.

O que pode ser herdado?

  • Todos public campos e métodos protected e public do pai

O que não pode ser herdado?

  • campos e métodos private
  • Construtores Embora, o construtor da subclasse tenha que chamar o construtor da superclasse se ele estiver definido (mais sobre isso depois!)
  • Múltiplas aulas Java suporta apenas herança única , ou seja, você pode herdar apenas uma classe por vez.
  • Campos. Campos individuais de uma classe não podem ser substituídos pela subclasse.

Tipo de fundição e referência

Em Java, é possível referenciar uma subclasse como uma instância de sua superclasse. É chamado Polimorfismo na Programação Orientada a Objetos (OOP), a capacidade de um objeto assumir muitas formas. Por exemplo, o objeto de classe Car pode ser referenciado como uma ocorrência de classe de Vehicle como esta:

Vehicle car = new Car(); 

Embora o contrário não seja possível:

Car car = new Vehicle(); // ERROR 

:rocket: Executar código

Como você pode fazer referência a uma subclasse Java como uma instância de superclasse, é possível converter facilmente uma instância de um objeto de subclasse em uma instância de superclasse. É possível converter um objeto de superclasse em um tipo de subclasse, mas apenas se o objeto for realmente uma instância da subclasse . Então tenha isso em mente:

Car car = new Car(); 
 Vehicle vehicle = car; // upcasting 
 Car car2 = (Car)vechile; //downcasting 
 
 Bike bike = new Bike(); // say Bike is also a subclass of Vehicle 
 Vehicle v = bike; // upcasting, no problem here. 
 Car car3 = (Car)bike; // Compilation Error : as bike is NOT a instance of Car 

:rocket: Executar código

Agora você sabe como compartilhar código por meio de um relacionamento pai-filho. Mas, e se você não gostar da implementação de um método específico na classe filha e quiser escrever um novo para ele? O que fazes, então?

Anule isso!

Java permite substituir ou redefinir os métodos definidos na superclasse. Por exemplo, sua classe Car tem uma implementação diferente de start() que o Vehicle pai, portanto, faça isso:

public class Vehicle { 
    public void start() { 
      System.out.println("Vehicle start code"); 
    } 
 } 
 
 public class Car extends Vehicle { 
    public void start() { 
      System.out.println("Car start code"); 
  } 
 } 
 
 Car car = new Car(); 
 car.start(); // "Car start code" 

:rocket: Executar código

Portanto, é muito simples substituir métodos na subclasse. Embora, existe uma captura. Apenas o método da superclasse com a mesma assinatura de método do método da subclasse será substituído. Isso significa que a definição do método da subclasse deve ter exatamente o mesmo nome, o mesmo número e tipo de parâmetros e exatamente a mesma sequência. Assim, o public void start(String key) não substitui o public void start() .

Notas :

  • Você não pode sobrescrever métodos privados da superclasse. (Muito óbvio, não é?)
  • E se o método da superclasse que você está ignorando na subclasse for subitamente obliterado ou os métodos alterados? Ele falharia em tempo de execução! Então, Java fornece uma anotação bacana @Override que você pode colocar sobre o método da subclasse, que irá avisar o compilador desses incidentes!

Anotações em Java é uma boa prática de codificação, mas elas não são uma necessidade. O compilador é inteligente o suficiente para descobrir sozinho. Ao contrário de outras linguagens OOP, o Annotations in Java não modifica necessariamente o método nem adiciona funcionalidades extras.

Como chamar métodos de superclasse?

Engraçado você pergunta sobre isso! Basta usar a palavra super chave super :

public class Vehicle() { 
    public void start() { 
      System.out.println("Vehicle start code"); 
    } 
 } 
 
 public class Car extends Vehicle { 
    public void run() { 
      super.start(); 
  } 
 } 
 
 Car car = new Car(); 
 car.run(); // "Vehicle start code" 

:rocket: Executar código

NB : Embora você possa chamar o método pai usando uma super chamada, não é possível subir a hierarquia de herança com super chamadas encadeadas.

Como saber o tipo de uma aula?

Usando o instanceof palavra-chave. Tendo muitas classes e subclasses, seria um pouco confuso saber qual classe é uma subclasse de qual em tempo de execução. Assim, podemos usar instanceof para determinar se um objeto é uma instância de uma classe, uma instância de uma subclasse ou uma instância de uma interface.

Car car = new Car(); 
 
 boolean flag = car instanceof Vehicle; // true in this case! 

Construtores e Herança

Como mencionado anteriormente, os construtores não podem ser diretamente herdados por uma subclasse. Embora, uma subclasse seja necessária para chamar o construtor de seu pai como a primeira operação em seu próprio construtor. Como? Você adivinhou, usando super :

public class Vehicle { 
    public Vehicle() { 
        // constructor 
    } 
    public void start() { 
      System.out.println("Vehicle start code"); 
    } 
 } 
 
 public class Car extends Vehicle { 
    public Car() { 
      super(); 
    } 
    public void run() { 
      super.start(); 
  } 
 } 

:rocket: Executar código

Lembre-se, se a superclasse não tiver nenhum construtor definido, você não precisará chamá-lo explicitamente na subclasse. Java manipula isso internamente para você! A invocação para o super construtor é feita no caso em que a superclasse deve ser chamada com qualquer outro construtor que não seja o construtor padrão .

Se nenhum outro construtor for definido, Java chamará o construtor de super classe padrão ( mesmo que não definido explicitamente ).

Parabéns, agora você sabe tudo sobre herança! Leia mais sobre formas avançadas de herdar coisas em Classes Abstratas e Interfaces !