Boas práticas com Orientação a Objetos. Paulo Silveira

Documentos relacionados
Orientação a Objetos - Herança

Tipos, Literais, Operadores

Tipos, Literais, Operadores

Programação Orientada a Objetos Classes Abstratas. Sérgio Soares

p Imagine que um Sistema de Controle do Banco pode ser acessado, além dos Gerentes, pelos Diretores do Banco

Lista 05 Herança. public class PessoaFisica extends Pessoa { private String RG; public PessoaFisica(){ super(); } public String getrg(){ return RG; }

Repetindo mais código?

Universidade de Mogi das Cruzes Implementação Orientada a Objetos - Profª. Danielle Martin. Guia da Sintaxe do Java

Interfaces POO. Prof. Marcio Delamaro

Palavras Reservadas da Linguagem Java

Encapsulamento. Alberto Costa Neto DComp - UFS

Programação Estruturada e Orientada a Objetos

Encapsulamento e Métodos (Construtores e Estáticos) João Paulo Q. dos Santos

Programação Orientada a Objetos

UNIP - Ciência da Computação e Sistemas de Informação. Estrutura de Dados. AULA 5 Pilhas

Computação II - Java - Prova 1 Prof. Adriano Joaquim de Oliveira Cruz /05/13. Questão: Total Pontos: Gráu:

Classes Abstratas e Interfaces AULA 12

Linguagem de Programação Orientada a Objeto Abstração - Encapsulamento

UNIVERSIDADE FEDERAL DE MATO GROSSO DO SUL SISTEMAS DE INFORMAÇÃO - CÂMPUS DE COXIM FUNDAMENTOS EM ORIENTAÇÃO A OBJETOS

Java para Desktop. Programação Orientada à Objetos 2 JSE

Singleton. Como a maioria dos programadores organizaria o código para acessar informação de configuração? Eis um exemplo:

Modificadores de Acesso e Atributos de Classe

Classes e Objetos. Prof. Fernando V. Paulovich 9 de agosto de 2010

Prova 2 PMR2300 1o. semestre 2015 Prof. Thiago Martins

p Imagine que um Sistema de Controle do Banco pode ser acessado, além dos Gerentes, pelos Diretores do Banco

Introdução à Orientação a Objetos em Java

UNIVERSIDADE FEDERAL DE MATO GROSSO DO SUL SISTEMAS DE INFORMAÇÃO - CÂMPUS DE COXIM FUNDAMENTOS EM ORIENTAÇÃO A OBJETOS

CIÊNCIA DA COMPUTAÇÃO - LINGUAGEM DE PROGRAMAÇÃO II REVISÃO POO

Programação Orientada a Objetos. Vagner Luz do Carmo - Vluzrmos

Orientação a Objetos AULA 09

Universidade Federal de Uberlândia Faculdade de Computação Programação Orientada a Objetos II Prof. Fabiano Dorça. Padrão Observer (Observador)

Introdução à Programação Orientada a Objetos. Programação Estruturada vs Programação Orientada a Objetos

Java First-Tier: Aplicações. Herança: Simples Múltipla. Orientação a Objetos em Java (III) Problemas de Herança Múltipla.

nome = n; cargo = c; salario = s; public void print() { System.out.println(nome cargo salario); public void aumento( double fator){

Objetivo: Aplicar a técnica de encapsulamento no sistema de gestão acadêmica

Classe Abstrata e Interface

Composite. Pronunciação americana: compósit Pronunciação canadense (Britânica): cómposit

Aula 5 POO 1 Encapsulamento. Profa. Elaine Faria UFU

Linguagem de programação Programação Orientada a objetos

Programação Orientada a Objetos II

Linguagem Java - Introdução

Programação de Computadores - I. Profª Beatriz Profº Israel

MsC. João Maria MsC. Liviane Melo

Programação Orientada a Objetos

Avançando em Java com Polimorfismo. Prof.: Hugo Barros

Java na Prática. Célio Silva Aula 3


Java Básico. Carga Horária: 32 horas. Pré-requisito: Lógica de Programação; JAVA. Conteúdo Programático

Encapsulamento e Modularização

Encapsulamento e Modularização

Programação Orientada a Objetos

Visitor. Um problema a resolver. Temos uma hierarquia de classes, provavelmente um Composite Exemplo: Numa rede elétrica, temos a seguinte hierarquia:

Orientação a Objetos. Fernando Camargo 5 de junho de 2017

Paradigmas de Linguagens de Programação. Suporte para Programação Orientada a Objeto

Construtores e Especificadores de Acesso

Prova de Recuperação PMR3201/PMR2300 1o. semestre 2015 Prof. Thiago Martins

Programação. Orientada a Objetos: Herança. Objetos. Relacionamento entre classes. Análise e Projeto Orientados a. Objetos

Programação Orientada a Objetos Flávio de Oliveira Silva 144

Linguagem de Programação II Implementação

Programação Orientada a Objectos - P. Prata, P. Fazendeiro

4 Conceito de Herança

JUnit. Alexandre Menezes Silva Eduardo Manuel de Freitas Jorge

Paradigmas de Programação. Java First-Tier: Aplicações. Orientação a Objetos em Java (I) Nomenclatura. Paradigma OO. Nomenclatura

Apêndice A. Alguns construtores e métodos importantes e úteis da classe Vector são:

Interfaces e polimorfismo

Tabelas de Dispersão. Estrutura de Dados e Algoritmos

Programação Orientada por Objectos 2010/11. 2º Exame 28 de Junho de 2011

Herança. Prof. Fernando V. Paulovich 23 de agosto de 2010

Universidade Federal de Uberlândia

Computação II - Java - Teste 1.2 Prof. Adriano Joaquim de Oliveira Cruz 2015/04/27

Coleções. João Paulo Q. dos Santos

Análise de Programação

Interfaces. Universidade Católica de Pernambuco Ciência da Computação. Prof. Márcio Bueno.

Recapitulando. Construtores: (Overload assinatura) public Circle() {...} public Circle(double x, double y, double r) {... }

Linguagem de Programação II Implementação

PROJETO DE DADOS PROJETO ARQUITETURAL BÁSICO. Projeto de Programas PPR0001

Encapsulamento. Separa a interface de um objeto dos detalhes de seu funcionamento interno. Caixa preta 2/27

O JUnit permite a realização de testes de unidades, conhecidos como "caixa branca", facilitando assim a correção de métodos e objetos.

Orientação a objetos. Programação. Orientada a Objetos. Orientação a objetos. Orientação a objetos. Abstração e encapsulamento

JAVA. José de Siqueira UFMG - ICEx - DCC

Programação Orientada a Objetos. Prof. Diemesleno Souza Carvalho

[Desenvolvimento OO com Java] Modificadores de acesso e atributos de classe

GRASP. Nazareno Andrade (baseado em Hyggo Almeida e Jacques Sauvé)

Herança e Polimorfismo

Programação Orientada a Objectos - P. Prata, P. Fazendeiro

Sintaxe Geral Tipos de Dados. Prof. Angelo Augusto Frozza, M.Sc.

Padrão de projeto de software

Fabrício J. Barth. BandTec - Faculdade de Tecnologia Bandeirantes

9 Classes Abstractas e Interfaces

Introdução. LP OO desenvolvida pela Sun no início da década de 90 com sintaxe semelhente a C\C++. C C++.

POO29004 Programação Orientada a Objetos

Herança. Herança. Herança. Herança. Herança. Programação Orientada a Objetos

Compiladores Análise Semântica

Linguagem de Programação III

Programação Orientada a Objetos II

RESULUÇÃO DOS EXERCÍCIOS E INSTRUÇÕES DE DECISÃO (if{} e else{}) Profº André Aparecido da Silva Disponível em:

Transcrição:

Boas práticas com Orientação a Objetos Paulo Silveira paulo.silveira@caelum.com.br

Rapidissímo overview IFs e switches X herança Vantagens e desvantagens do uso de Herança Casos errados do uso de herança Herança versus Composição Herança versus Interfaces Programando pensando em Interfaces

Antes de qualquer coisa: Não estou falando mal do seu código!

Switchs e IFs Usando polimorfismo

Caso trivial class Funcionario { private int codigo; public static final int DIRETOR = 1; public static final int PRESIDENTE = 2; //... public int getcodigo() { return this.codigo;

Em algum outro lugar.. class Relatorio { private double dinheirogasto; private Empresa empresa; //... public void adiciona(funcionario f) { switch (f.getcodigo()) { case Funcionario.DIRETOR : this.gastos += 1.1 * f.getsalario(); break; case Funcionario.PRESIDENTE : this.gastos += f.getsalario() + empresa.getpartedoslucros(); break; Esse tipo de código vai se espalhar por toda aplicação! Ao criar uma nova filha de Funcionario, precisamos mudar esse(s) código(s)!

Remodelando Funcionario class Funcionario { public double getgastos() { return this.salario; class Diretor extends Funcionario { public double getgastos() { return this.salario * 1.1; Diretor Presidente Cálculo dos gastos concentrado dentro da própria classe

E o relatório... class Relatorio { private double dinheirogasto; private Empresa empresa; //... public void adiciona(funcionario f) { this.gastos += f.getgastos(); Para adicionar uma nova classe que extende Funcionario, não teremos mais de mexer na classe Relatorio!

Controle de Permissões class Usuario { private int id; private String name; //... O uso de herança nesse caso é altamente dicutível! Moderador Usuario Administrador Estamos usando apenas como exemplo.

Primeira tentativa Ifs encadeados num estilo switch(int) public void apagaregistro() { if(this.user instanceof Usuario) { return false; if(this.user instanceof Moderador) { return false; if(this.user instanceof Administrador) { return true; Caso uma classe Colaborador fosse adicionada, precisaríamos mexer aqui também!

Usando polimorfismo Usuario Moderador Administrador class Usuario { public boolean hasright(int code) {

Apagando com a nova forma public void apagaregistro() { if(this.user instanceof Usuario) { return false; if(this.user instanceof Moderador) { return false; if(this.user instanceof Administrador) { return true; Passa para: public void apagaregistro() { if(this.user.hasright(permissions.delete){ return false;

E ao criarmos a classe Colaborador... class Colaborador extends Usuario { public boolean hasright(int code) { // monte de ifs e switchs Código de permissões não esta mais concetrado em um único lugar, cada classe é responsável pelo seu.

Pequena conclusão Switch é uma anomalia Polimorfismo é muito mais elegante Você muda apenas na própria classe, não precisa concentrar lógica de negócio. Switch é feio! Isto não é uma regra rígida!

Vantagens da Herança

Herança, quais são as vantagens? Reaproveitamento de código Possibilita polimorfismo Vamos mostrar que podemos ter esses benefícios de outras maneiras mais leves.

Quando não usar herança Apredendo com os erros da Sun

O que vocês acham dessas classes? java.util.properties java.util.stack

Properties public class Properties extends Hashtable Properties é uma Hashtable? Hashtable: associa Object Object Properties: associa String - String Properties não é uma Hashtable!

Properties Object Dictionary Hashtable Properties

O que acontece com esse código? Object object = new Object(); Hashtable table = new Properties(); table.put( x, object); table.get( x ); Funciona ok!

Um pouco pior... Object object = new Object(); Properties table = new Properties(); table.put( x, object); table.getproperty( x ); table.get( x ); Compila perfeitamente, mas só retorna o object quando chamado pelo.get, e pelo getproperty volta Null. Como adivinhariamos isso? Parece então que são duas tabelas separadas. Uma para Object- Object, e outra para String String

Último round Properties table = new Properties(); table.put( x, y ); table.getproperty( x ); Retorna null também? Não, dessa vez acontece o esperado.

java.util.stack Caso parecido Se é uma pilha, porque posso remove(int)? Porque posso add(int, Object)? Herdou apenas para não ter de escrever um vetor! PREGUIÇA!

Pequena conclusão Nunca usar herança quando a relação não é claramente é um. Contratos acabam sendo quebrados Difícil de mudar depois Pergunte a si mesmo se você não está fazendo isso por pura preguiça!

Lembram-se desse caso? Moderador é um Usuario? Usuario Usuario as vezes esta no papel de moderador ou administrador, mas a relação não é exatamente é um. Moderador Administrador

Classe Entity class Entity { private int id; private String name; private String description; // gets e sets class Usuario extends Entity { é um faz sentido? É um estado de Usuário? É um papel de Usuário? Veremos como resolver isso com composição!

Problemas trazidos pela herança

Considere Funcionario Diretor Presidente

Uso do protected class Funcionario { protected double salario; protected int idade; class Diretor extends Funcionario { public double getgastos() { if(this.idade < 35) { return salario; else { return salario * 1.1;

Uso do protected class Funcionario { protected double salario; protected int idade; O que acontece com a classe Diretor? Não compila? Isto não é o mais grave, ele poderia estar em outro jar, e ele vai começar a lançar Errors class Funcionario { protected double salario; protected Calendar nascimento;

Uso do protected Classe filha precisa conhecer bem a mãe Classe mãe não pode mudar sua representação interna com facilidade! Quebra de encapsulamento. Protected define um contrato forte para a mãe que não tem muito utilidade para quem esta de fora! Métodos protected não são tão malvados assim

Considere Pessoa Pessoa Física Pessoa Jurídica

Método na mãe muda Quando um método da mãe muda pode quebrar o comportamento da classe filha

Conhecemos a interface publica da classe class PessoaJuridica { public void adicionanota(nota nota) { public void adicionavariasnotas(list<nota> notas) { Não conhecemos bem essa classe!

Fornecedor quer saber quantas transcoes! class FornecedorJuridica extends PessoalJuridica { private int transacoes; public void adicionanota(nota nota) { this.transacoes++; Funciona? super.adicionanota(nota); public void adicionavariasnotas(list<nota> notas) { this.transacoes += notas.size(); super.adicionavariasnotas(notas); public int gettransacoes() { return this.transacoes; List notas =... // lista com 3 notas f.adicionavariasnotas(notas); f.gettotaltransacoes();

Depende! List notas =... // lista com 3 notas f.adicionavariasnotas(notas); f.gettotaltransacoes(); class PessoaJuridica { Resultado? public void adicionanota(nota nota) { this.vetorzinho[posicao++] = nota; public void adicionavariasnotas(list<nota> notas) { for(nota n : notas) { this.vetorzinho[posicao++] = n;

Mudança na classe mãe! List notas =... // lista com 3 notas f.adicionavariasnotas(notas); f.gettotaltransacoes(); E agora que mamãe mudou? class PessoaJuridica { public void adicionanota(nota nota) { this.vetorzinho[posicao++] = nota; public void adicionavariasnotas(list<nota> notas) { for(nota n : notas) { //... this.adicionanota(n); A resposta é 6!

Grande árvore de herança, mais problemas Pessoa Pessoa Física Pessoa Jurídica Fornecedor Físico Fornecedor Jurídico

Herança, lados negativos Você ganha mais coisas do que gostaria Sua relação com sua mãe é conturbada Quebra de encapsulamento Não use herança apenas por reaproveitamento de código da classe mãe! Não use herança apenas pelo polimorfismo!

Herança versus Composição Usando polimorfismo

Problemas! Além dos já apresentados: Pessoa Fornecedor é Pessoa? Pessoa Física Pessoa Jurídica Aqui tem código repetido! Fornecedor Físico Fornecedor Jurídico

FornecedorJuridico é Pessoa? É sim, mas estamos utilizando algo como Pessoa p = new Fornecedor()? Ou recebendo Fornecedor como Pessoa? Aumentado a hierarquia, como representaríamos alguem como Fornecedor e Consumidor?

Diminuindo acomplamento Pessoa Fornecedor Físico Pessoa Física class FornecedorFisico extends PessoaFisica { passa para: class FornecedorFisico { private PessoaFisica pessoa; // metodos para delegar

Acabando com código duplicado Pessoa Fornecedor Físico Pessoa Física Pessoa Jurídica Fornecedor Jurídico public String peganome() { public void envianotificacaosobrecredito() {

Acabando com código duplicado Pessoa Fornecedor Físico Pessoa Física Pessoa Jurídica Fornecedor Jurídico Fornecedor Helper

FornecedorHelper Faz o trabalho comum aos Fornecedores Pode ser uma classe package-friendly class FornecedorHelper { private String nome; private String email; public String peganome() { public void envianotificacaosobrecredito() { class FornecedorJuridico { private FornecedorHelper helper; public void envianotificacaosobrecredito() { this.helper.envianotificacaosobrecredito();

Vantagens do uso da composição Menor acoplamento, difícil de quebrar Quem faz e como faz esta escondido Implementação pode ser trocada em runtime

Antes de usar herança Estou fazendo por preguiça? É uma relação de é um? Não é um estado em que a classe pode ficar? Não é um papel que a classe pode tomar?

Será que isso pode causar transtornos? Object Component Container JComponent JPanel JSpinner.DefaultEditor JSpinner.DateEditor

Herança versus Interfaces Programando voltado para interfaces

E se eu precisasse de polimorfismo? Utilização de Interfaces Reaproveitamento por composição Classes abstratas na hora da preguiça! Talvez package-friendly

Entity como interface interface Entity { Entity int getid(); Usuario class Usuario implements Entity { //... public int getid() { return this.id;

Entity melhorada Entity Usuario EntityInfo class Usuario implements Entity { private EntityInfo info; public int getid() { return this.info.getid();

Temos de escrever o esqueleto sempre? Entity Abstract Entity EntityInfo Usuario

Regras do Gang of Four 1. Prefira composição em vez de herança 2. Programe pensando nas interfaces e não na implementação

Leitura recomendada Design Patterns, Gang of Four Effective Java, Joshua Bloch Refactoring, Martin Fowler

Obrigado! Perguntas e Respostas Você pode ver esta palestra em: http://www.paulo.com.br/ Agradecimentos: Nos vemos no BrasilOne! http://www.brasilone.com.br/