36
Polimorfismo Universidade Federal de Uberlândia Faculdade de Computação Disciplina – POO1 Prof. Fabiano Dorça

Universidade Federal de Uberlândia Faculdade de Computação ...fabiano/disciplinas/poo1/Aula08-Polimorfismo.pdf · Polimorfismo Polimorfismo significa "muitas formas". Permite ao

  • Upload
    dotruc

  • View
    216

  • Download
    0

Embed Size (px)

Citation preview

Polimorfismo

Universidade Federal de UberlândiaFaculdade de Computação

Disciplina – POO1

Prof. Fabiano Dorça

Polimorfismo

● Polimorfismo significa "muitas formas".

● Permite ao desenvolvedor usar o mesmo elemento de formas diferentes.

● Situação na qual um objeto pode responder de maneiras diferentes ao receber uma mensagem.

Polimorfismo

● O polimorfismo pode ocorrer quando:– há sobreposição de métodos da superclasse nas

subclasses.

● Em tempo de execução o polimorfismo ocorre através de ligação dinâmica (dynamic binding).

● O método a ser executado é determinado apenas em tempo de execução (e não em tempo de compilação).

Polimorfismo

● Quando um método é chamado...

– a classe de instanciação do objeto (não a classe de declaração) dita a implementação a ser usada.

Polimorfismo

● A classe de declaração de um objeto é determinada em tempo de compilação.

– O compilador tem acesso a essa informação na própria declaração da referência.

Polimorfismo

● Exemplo:

Funcionario f;f = new Professor();…?f.calcSalario();…?f.calcSalario();

Polimorfismo

● O polimorfismo permite “programar no geral” em vez de “programar no específico”.

● Escrever programas que processam objetos que compartilham a mesma superclasse.

Polimorfismo

● Exemplo: calculo do imposto de funcionários

Polimorfismo

● Exemplo: calculo do imposto de funcionários

public abstract class Funcionario{…public abstract double calcSalario();

}

public class Supervisor extends Funcionario{...public double calcSalario(){ return ....}

}

Polimorfismo

public class Vendedor extends Funcionario{...public double calcSalario(){ return ....}

}

public class Gerente extends Funcionario{...public double calcSalario(){ return ....}

}

Polimorfismo

→ Deve ser criado um método na classe FolhaPagamento capaz de calcular o imposto de renda a ser pago pelos funcionários

→ Mas independentemente do tipo de funcionário, a forma de calcular o imposto é o mesmo...

Polimorfismo

public class FolhaPagamento{ … public double calcImpVend(Vendedor v){ return v.calcSalario() * 0.275; } public double calcImpSup(Supervisor s){ return s.calcSalario() * 0.275; } public double calcImpGerente(Gerente g){ return g.calcSalario() * 0.275; }}

Polimorfismo

● Considerando o polimorfismo, e a máxima “programe para o geral, e não para o específico”...

→ poderíamos criar um método geral para cálculo do imposto de qualquer tipo de funcionário.

Polimorfismo

public class FolhaPagamento{ … public double calcImposto(Funcionario f){ return f.calcSalario() * 0.275; }

Chamada polimórfica ao método calcImposto()

Polimorfismo

● Exemplo:

– Suponha a seguinte hierarquia de classes:

Polimorfismo

public abstract class Forma{ public abstract float calcularArea(); public abstract float calcularPerimetro();}

Polimorfismo

public class Circulo extends Forma{ private float raio; … public float calcularArea(){ return Math.PI * raio * raio; } public float calcularPerimetro(){ return 2 * Math.PI * raio; }}

Polimorfismo

public class Retangulo extends Forma{ private float altura, base; … public float calcularArea(){ return altura * base; } public float calcularPerimetro(){ return 2 * (altura+base); }}

Polimorfismo

● Podemos atribuir a “f ” objetos de qualquer subclasse de Forma:

Forma f;f = new Circulo();f.calcularArea();…f = new Retangulo();…f.calcularArea();f = new Quadrado();

Polimorfismo

● Desta forma, poderíamos pensar em um método genérico para desenhar formas:

public abstract class Desenho{ public static void desenhar(Forma f) { System.out.println(f.getClass().getName()); System.out.println(“Área: ”+f.calcularArea()); }}

● Em tempo de execução, qual será a saída?

Polimorfismo

● Como o método desenhar recebe uma forma, poderíamos fazer:

Circulo c = new Circulo();…Retangulo r = new Retangulo();…Desenho.desenhar(c);Desenho.desenhar(r);...

Polimorfismo

● Exemplo: Implementação de um jogo

public class Jogador{

public void atirar(Revolver r){ r.atirar(); }

public void explodir(Bomba b){ b.explodir(); }}

Polimorfismo

public class Revolver{ public void atirar(){ System.out.println(“atirando...”); }}

public class Bomba{ public void explodir(){ System.out.println(“explodindo...”); }}

Polimorfismo

● Problemas com este projeto?

– Sempre que novas armas forem introduzidas no jogo, a classe jogador sofrerá alterações...

– Difícil manutenção– Possível replicação de código

PolimorfismoIntrodução de novas armas implicam em alterações na classe Jogador...

public class Jogador{ ... public void atirar(Revolver r){ r.atirar(); } public void explodir(Bomba b){ b.explodir(); } public void lançar(Dardos d){ d.lançar(); }}

Polimorfismo

● Solução: – criação de uma abstração para armas através do

uso de herança.– Uso de polimorfismo em jogador.

Polimorfismo

public abstract class Arma{ public abstract void usar();}

public class Revolver extends Arma{ public void usar(){ System.out.println(“atirando...”); }}

public class Bomba extends Arma{ public void usar(){ System.out.println(“explodindo...”); }}

Polimorfismo

public class Jogador{ public void usarArma (Arma a) { a.usar(); }}

Polimorfismo

● Através do polimorfismo poderia ocorrer:

Jogador j = new Jogador();…Revolver r = new Revolver();Bomba b = new Bomba();…j.usarArma(r);...j.usarArma(b);

Polimorfismo

● Polimorfismo em ArrayLists

Um ArrayList para armazenar circulos, retangulos e quadrados:

ArrayList<Forma> a = new ArrayList<Forma>();

Polimorfismo

Métodos que recebem diversos tipos de ArrayList

Exemplo:

public void desenhar(ArrayList<? extends Forma>){

}

→ Neste caso, o método pode receber como entrada um ArrayList de qualquer coisa que estenda forma, por exemplo, ArrayList<Circulo> ; ArrayList<Retangulo> ; ArrayList<Quadrado>

Polimorfismo

● Qual a diferença?

public void desenhar(ArrayList<? extends Forma>){

}

public void desenhar(ArrayList<Forma>){

}

Polimorfismo

● Com o polimorfismo, podemos projetar sistemas facilmente extensíveis.

– Novas funcionalidades são adicionadas com pouca ou nenhuma modificação a partes gerais do programa.

– A adição de novas classes não tem impacto no código que já está pronto.

– Desta forma, todo código deve ser escrito para uma abstração e não para uma classe concreta.

Polimorfismo

● Exercícios:

– Desenhe o diagrama de classes da primeira implementação do jogo.

– Desenhe o diagrama de classes da segunda implementação do jogo e compare-os.

– Insira novas armas na implementação polimórfica do jogo, observando a facilidade de extensão da aplicação.

– Crie uma classe FabricaInimigo cujo método fabricar() deve instanciar e retornar aleatóriamente um sub-tipo de inimigo a cada chamada.

Referências

BOOCH, G. Object-Oriented Analysis and Design with Applications, 3a Edição. Addison-Wesley, 2007.BOOCH, G., RUMBAUGH, J., JACOBSON, I. UML, Guia do Usuário. Rio de Janeiro: Campus, 2000.DEITEL, H. M.; DEITEL P. J. Java: Como Programar, 6a. Edição. Pearson, 2005. (Livro Texto)FOWLER, M. UML Essencial, 2a Edição. Bookmann, 2000.HORSTMANN, C.; CORNELL, G. Core Java 2 - Fundamentals, 7a. Edição. Prentice Hall, 2004.LARMAN, C. Utilizando UML e Padrões: Uma Introdução à Análise e ao Projeto Orientado a Objetos. PortoAlegre: Bookmann, 2001.RUMBAUGH, J.; BLAHA, M. Modelagem e Projetos Baseados em Objetos com UML 2, 1a Edição. EditoraCampus, 2006