1. Habilidades
Para entender melhor os benefícios das interfaces e onde usá-las, precisamos falar sobre algumas coisas mais abstratas.
Uma classe geralmente modela um objeto específico. Uma interface corresponde menos a objetos e mais a suas habilidades ou funções.
Por exemplo, coisas como carros, bicicletas, motocicletas e rodas são melhor representadas como classes e objetos. Mas suas habilidades - como "Posso ser montado", "Posso transportar pessoas", "Posso ficar de pé" - são melhor apresentadas como interfaces. aqui estão alguns exemplos:
Código | Descrição |
---|---|
|
Corresponde à capacidade de movimento |
|
Corresponde à capacidade de ser montado |
|
Corresponde à capacidade de transportar coisas |
|
A Wheel classe pode se mover |
|
A Car classe pode se mover, ser montada e transportar coisas |
|
A Skateboard classe pode se mover e ser montada |
2. Funções
Interfaces simplificam muito a vida de um programador. Muitas vezes, um programa tem milhares de objetos, centenas de classes, mas apenas algumas dezenas de interfaces , ou seja, funções . Existem poucos papéis, mas existem muitas maneiras de combiná-los (classes).
O ponto principal é que você não precisa escrever código em cada classe para interagir com todas as outras classes. Você só precisa interagir com suas funções (interfaces).
Imagine que você é um treinador de animais de estimação. Cada um dos animais de estimação com os quais você trabalha pode ter várias habilidades diferentes. Você entra em uma discussão amigável com seu vizinho sobre quais animais de estimação podem fazer mais barulho. Para resolver o problema, basta alinhar todos os bichinhos que podem "falar" e dar a eles o comando: Fale!
Você não se importa que tipo de animal eles são ou que outras habilidades eles têm. Mesmo que eles possam dar uma cambalhota tripla para trás. Neste momento específico, você está interessado apenas em sua capacidade de falar alto. Veja como ficaria no código:
Código | Descrição |
---|---|
|
A CanSpeak habilidade. Essa interface entende o comando to speak , o que significa que possui um método correspondente. |
|
Animais que possuem esta característica.
Para facilitar o entendimento, disponibilizamos os nomes das turmas em inglês. Isso é permitido em Java, mas é altamente indesejável.
|
|
E como damos a eles o comando? |
Quando o número de aulas em seus programas chegar aos milhares, você não conseguirá viver sem interfaces. Em vez de descrever a interação de milhares de classes, basta descrever a interação de algumas dezenas de interfaces — isso simplifica muito a vida.
E quando combinada com o polimorfismo, essa abordagem geralmente é um sucesso estrondoso.
3. A default
implementação de métodos de interface
Classes abstratas podem ter variáveis e implementações de métodos, mas não podem ter herança múltipla. As interfaces não podem ter variáveis ou implementações de métodos, mas podem ter herança múltipla.
A situação é expressa na tabela a seguir:
Habilidade/propriedade | aulas abstratas | Interfaces |
---|---|---|
Variáveis | ✔ | ✖ |
Implementação do método | ✔ | ✖ |
Herança múltipla | ✖ | ✔ |
Portanto, alguns programadores realmente queriam que as interfaces tivessem a capacidade de ter implementações de método. Mas ter a capacidade de adicionar uma implementação de método não significa que um sempre será adicionado. Adicione se quiser. Ou se você não fizer isso, então não faça.
Além disso, os problemas com herança múltipla são principalmente devidos a variáveis. De qualquer forma, foi o que eles decidiram e fizeram. A partir do JDK 8, o Java introduziu a capacidade de adicionar implementações de método às interfaces.
Aqui está uma tabela atualizada (para JDK 8 e superior):
Habilidade/propriedade | aulas abstratas | Interfaces |
---|---|---|
Variáveis | ✔ | ✖ |
Implementação do método | ✔ | ✔ |
Herança múltipla | ✖ | ✔ |
Agora, para classes abstratas e também para interfaces, você pode declarar métodos com ou sem implementação. E esta é uma excelente notícia!
Nas classes abstratas, os métodos sem implementação devem ser precedidos pela abstract
palavra-chave. Você não precisa adicionar nada antes dos métodos com uma implementação. Nas interfaces, o oposto é verdadeiro. Se um método não tiver uma implementação, nada deverá ser adicionado. Mas se houver uma implementação, a default
palavra-chave deve ser adicionada.
Para simplificar, apresentamos essas informações na tabelinha a seguir:
Habilidade/propriedade | aulas abstratas | Interfaces |
---|---|---|
Métodos sem implementação | abstract |
– |
Métodos com uma implementação | – | default |
Problema
O uso de interfaces que possuem métodos pode simplificar muito as hierarquias de classes grandes. Por exemplo, o resumo InputStream
e OutputStream
as classes podem ser declarados como interfaces! Isso nos permite usá-los com muito mais frequência e de maneira muito mais conveniente.
Mas já existem dezenas de milhões (bilhões?) de classes Java no mundo. E se você começar a alterar as bibliotecas padrão, poderá quebrar alguma coisa. Como tudo! 😛
Para não interromper acidentalmente os programas e bibliotecas existentes, foi decidido que as implementações de métodos em interfaces teriam a menor precedência de herança .
Por exemplo, se uma interface herda outra interface que possui um método e a primeira interface declara o mesmo método, mas sem uma implementação, a implementação do método da interface herdada não alcançará a interface herdada. Exemplo:
interface Pet
{
default void meow()
{
System.out.println("Meow");
}
}
interface Cat extends Pet
{
void meow(); // Here we override the default implementation by omitting an implementation
}
class Tom implements Cat
{
}
O código não compilará porque a Tom
classe não implementa o meow()
método.
GO TO FULL VERSION