• Nenhum resultado encontrado

5-PadroesdeProjeto

N/A
N/A
Protected

Academic year: 2021

Share "5-PadroesdeProjeto"

Copied!
145
0
0

Texto

(1)

Padrões de Projeto

Padrões de Projeto

(2)

Introdução

Introdução

Projetar software é uma tarefa difícil. A maioria dos projetistas é capaz de

compreender conceitos como classes, objetos, interfaces e herança.

O desafio reside em aplicá-los para construir software flexível e reutilizável.

Projetistas novatos tendem a se perder com as muitas opções disponíveis e

a recorrer a técnicas não orientadas a objetos com as quais têm certa

familiaridade.

Projetistas experientes, por sua vez, tendem a fazer bons projetos. Eles

sabem que não se deve resolver todo e qualquer problema partindo de

princípios básicos (classes, objetos, herança, relacionamentos,

agregação,...).

Ao contrário, deve-se buscar reutilizar soluções que funcionaram no

(3)

Padrões de Projeto - Cristiano Biancardi

Assim, um padrão é um par nomeado problema/solução, que pode ser

utilizado em novos contextos, com orientações sobre com utilizá-lo em

novas situações.

Padrões são destilações de sabedoria acumulada, fornecendo um

jargão-padrão e nomeando os conceitos que praticantes

experimentados aplicam.

Cada padrão sistematicamente nomeia, explica e avalia um importante

projeto que ocorre repetidamente em sistemas OO.

O objetivo de um design pattern é registrar uma experiência no projeto de

software OO, na forma de um padrão passível de ser efetivamente utilizado por

projetistas.

Um projetista familiarizado com padrões de projeto pode aplicá-los

diretamente a problemas de projeto sem ter que redescobrir abstrações e

os objetos que as capturam.

(4)

Em geral, um padrão tem quatro elementos essenciais:

Nome: identificação de uma ou duas palavras, que se possa utilizar

para descrever o problema de projeto, suas soluções e conseqüências.

Problema: descreve quando aplicar o padrão. Explica o problema de

projeto e seu contexto.

Solução: descreve os elementos que compõem o projeto, seus

relacionamentos, responsabilidades e colaborações. Não descreve um

particular projeto concreto ou implementação.

Um padrão provê uma descrição abstrata de um problema de projeto e

como uma organização geral de classes e objetos resolve este problema.

Conseqüências: são os resultados e os comprometimentos feitos ao

(5)

Padrões de Projeto - Cristiano Biancardi

A sigla “GoF”

“Gang of Four”

Apelido carinhoso pela qual o quarteto Erich Gamma,

Richard Helm, Ralph Johnson e John Vlissides

Ficou conhecido quando escreveram o livro “Design

Patterns”, no início da década de 90

Neste livro, os quatro dividiram um conjunto de 23

padrões em 3 grupos:

Estruturais: lidam com maneiras de se compor objetos.

Comportamentais: caracterizam formas de interação

entre objetos.

Criacionais: lidam com maneiras de se gerenciar a

(6)

Padrões Estruturais

Adapter

Façade

Composite

Bridge

Proxy

Flyweight

Decorator

(7)

Padrões de Projeto - Cristiano Biancardi

Adapter

Adapter

Permite que classes com interfaces

incompatíveis possam interagir.

Converte a interface de uma classe em outra

interface, permitindo que classes trabalhem em

conjunto, quando isto não seria possível por

causa da incompatibilidade de interfaces.

(8)

Figura 1: Plugue europeu

de três pinos

Figura 2: Tomada

comum de dois pinos

(9)
(10)

Façade

Façade

Fachada

Provê uma interface unificada para um conjunto de classes em um

subsistema.

Define uma interface de nível mais alto para o subsistema,

tornando-o mais fácil de ser usado.

Facilita o trabalho em subsistemas pois são fornecidas as interfaces

de cada subsistema.

Facilita a utilização do sistema: Cliente só precisa conhecer a fachada.

Promove acoplamento fraco:

(11)

Padrões de Projeto - Cristiano Biancardi

(12)

Existem circunstâncias onde é necessário

utilizar diversas classes diferentes para

que uma tarefa possa ser completada,

caracterizando uma situação onde uma

classe cliente necessita utilizar objetos de

um conjunto específico de classes

utilitárias que, em conjunto, compõem um

subsistema particular ou que representam

(13)
(14)

O Facade é um padrão que pode apresentar

infinidades de formas de representá-lo. O que

importa para este padrão é que o Cliente

apenas acesse objetos da classe Facade,

esperando algum resultado vindo dela. A classe

Facade é que terá a responsabilidade de entrar

em contato com as diversas instâncias dentro

deste sistema, efetuar possíveis cálculos vindos

de classes abaixo dela e retornar as respostas

que o cliente pediu.

(15)
(16)
(17)

Padrões de Projeto - Cristiano Biancardi

Implementação:

Implementar um Facade demanda definir um

conjunto de operações reduzidas que permita

ocultar a complexidade inerente à utilização de

várias classes de um subsistema.

(18)

Exemplo:

O cliente necessita consultar várias entidades a fim de saber se

têm condições de receber um empréstimo. Para isso,

normalmente, o cliente teria que conhecer toda a complexidade

envolvida com as regras de concessão de empréstimos e

aprende-las, no entanto, nada melhor do que deixar isso a cargo

de quem já está no sistema, no caso o Facade, que irá se

preocupar em colher dados das diferentes classes que podem

decidir sobre a possibilidade do empréstimo e retornará esta

informação pronta para o cliente.

FacadeApp é o cliente que busca informações que podem vir de

vários de subsistemas, Facade é a classe responsável por

acessar os subsistemas e trazer respostas de forma

transparente a quem esteja acessando o Facade. Banco,

Emprestimo, Crédito e Consumidor são classes pertencentes

aos subsistemas.

(19)
(20)

Composite

Composite

Compor objetos em estruturas de árvore

para representar hierarquias todo-parte.

Permite que clientes trate objetos

individuais e compostos de maneira

uniforme.

(21)

Padrões de Projeto - Cristiano Biancardi

Exemplo:

Existem gráficos que são compostos de outros

gráficos;

O programa tem que conhecer cada um deles,

(22)

Solução:

A classe abstrata representa tanto gráficos simples quanto compostos.

Programa só precisa conhecer Gráfico.

A agregação permite efetuar a composição em GráficoComposto.

(23)

Padrões de Projeto - Cristiano Biancardi

Bridge

Bridge

Desacopla uma abstração de sua

implementação.

Abstração e sua implementação variam

independentemente.

O padrão Bridge é útil quando se tem uma

abstração que tem diferentes implementações.

Exemplo Classico de Brigde: drivers

O projeto separa o desenvolvimento da aplicacao do

desenvolvimento dos drivers que implementam as

operações abstratas das quais as aplicacoes

(24)
(25)

Padrões de Projeto - Cristiano Biancardi

DrawRect()

DrawText()

Window

DrawText()

DrawRect()

WindowImp

DevDrawText()

DevDrawLine()

IconWindow

DrawBorder()

TransientWindow

DrawCloseBox()

XWindowImp

DevDrawText()

DevDrawLine()

PMWindowImp

DevDrawText()

DevDrawLine()

DrawRect()

XDrawLine()

XDrawString()

imp  DevDrawLine()

imp  DevDrawLine()

imp  DevDrawLine()

imp  DevDrawLine()

imp

bridge

(26)

Exemplo: usando o padrão Bridge para abstrair

o driver específico de banco de dados.

Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");

Class.forName("com.sybase.jdbc2.jdbc.SybDriver");

Class.forName cria uma instância do driver e regista-o no

(27)

Padrões de Projeto - Cristiano Biancardi

Proxy

Proxy

Procurador

É um objeto representante/procurador de

outro objeto para controlar o acesso ao

mesmo.

(28)

Contexto:

Um cliente precisa acessar um serviço de um outro componente

em um sistema distribuído.

O acesso direto é tecnicamente possível, mas pode não ser a

melhor opção.

Problema:

O acesso direto pode não ser eficiente em tempo de execução,

ter alto custo e não ser seguro.

Solução:

Utilize um representante no cliente que ofereça o serviço de

forma idêntica e realize pré- e pós-processamento adicionais

para garantir a Qualidade do Serviço.

(29)

Padrões de Projeto - Cristiano Biancardi

Objetivo principal:

encapsular um objeto através de um outro objeto que

possui a mesma interface, de forma que o segundo

objeto, conhecido como “Proxy”, controla o acesso ao

primeiro, que é o objeto real.

(30)

class BusinessComp

{

public void SaveOrder(Order order) {}

}

class BusinessCompProxy {

BusinessComp subject;

public void SaveOrder(Order order) {

using (TransactionScope scope = new TransactionScope () {

try {

subject.SaveOrder(order);

}

catch (Exception ex) {

LogException(ex);

throw;

}

(31)

Padrões de Projeto - Cristiano Biancardi

Flyweight

Flyweight

Peso-Pena

Uso de compartilhamento de objetos

visando melhorar a eficiência.

(32)
(33)

Padrões de Projeto - Cristiano Biancardi

Exemplo: Pool de Conexões

A maior parte das aplicações desenvolvidas normalmente

acessam banco de dados. Sempre que precisar acessar os

dados no servidor a aplicação o realizará através de um objeto

de conexão.

Para criar esta conexão é preciso informar a string de conexão,

que indica qual servidor e qual banco de dados será

estabelecida a conexão etc.

Em resumo, a string de conexão identifica o fornecedor do

banco de dados, nome da máquina onde a aplicação de banco

de dados está instalada, nome do banco de dados da aplicação,

informações de segurança (usuário, senha, autenticação

integrada etc) e parâmetros de controle do Pool de Conexões,

entre outras.

(34)

Imagine que sua aplicação tem uma tela que mostra alguns registros

resultantes de uma consulta.

Já percebeu que existe uma demora até que os dados sejam exibidos?

Boa parte desta demora é porque sua aplicação está criando uma conexão

com banco de dados.

Só que este processo de conexão não é tão simples e tem um custo

alto.

Por que? Porque uma conexão com banco de dados consiste de algumas

tarefas que consomem recursos:

uma comunicação física, por exemplo um Socket, precisa ser

estabelecida e para isso é necessário um handshake inicial entre

as máquinas; a string de conexão precisa ser analisada e validada;

a conexão deverá ser autenticada contra o servidor; algumas

verificações para registro numa transação corrente etc.

Como uma aplicação precisa interagir várias vezes com o banco de

dados, dependendo de como esteja sendo utilizada, o desempenho e a

escalabilidade da aplicação podem ser comprometidos.

(35)

Padrões de Projeto - Cristiano Biancardi

A maioria das aplicações usam uma ou poucas

configurações de banco de dados diferentes,

pois durante a execução da aplicação várias

conexões idênticas serão abertas e fechadas, o

que poderá impactar a performance da sua

aplicação.

Como resolver isso?

Reutilização das conexões.

O Pool de Conexões é um repositório que mantém

(36)

Decorator

Decorator

Decorador

Anexar responsabilidades adicionais a um

objeto dinamicamente.

Decorators oferecem uma alternativa flexível ao

uso de herança para estender uma

funcionalidade.“

Exemplo: um toolkit para a construção de

interfaces gráficas deve permitir adicionar

propriedades como bordas ou barras de

rolagem.

(37)
(38)
(39)
(40)

Em Java, o uso mais comum de

decoradores é nos objetos que

representam fluxos de entrada e saída

(I/O streams)

java.io: InputStream, OutputStream, Reader,

(41)
(42)
(43)

Padrões de Projeto - Cristiano Biancardi

Padrões Comportamentais

Caracterizam as maneiras pelas quais classes ou objetos interagem e

distribuem responsabilidades.

Chain of Responsability

Observer

Mediator

Memento

Template Method

State

Strategy

Command

Iterador

Interpreter

Visitor

(44)

Chain of Responsability

Chain of Responsability

Cadeia de Responsabilidade

Propósito é fazer com que uma coleção de objeto, em vez

de apenas um, forneça funcionalidade.

Aplicação cliente não tem que saber quais objetos são

responsáveis por qual parte da funcionalidade.

Apresenta uma interface simples

Exemplo:

Corretor ortográfico: conjunto de objetos fazendo a correção de

gramática, ortografia, estilo etc.

(45)
(46)

Observer

Observer

Observador

Intenção

Definir uma dependência um-para-muitos entre objetos de forma

que quando um objeto muda de estado, todos seus dependentes

são notificados e atualizados automaticamente.

Aplicação

Mudar um objeto causando mudanças em outros objetos, sendo

que não se sabe a priori quantos objetos precisam ser mudados.

Fazer um objeto notificar outros objetos de que seu estado

mudou, sem assumir nada sobre os outros objetos.

Exemplo:

Fundos múltiplos investem em ações, de modo que quando o preço

(47)
(48)

Mediator

Mediator

Mediador

Intenção:

Definir um objeto que encapsula a forma como um conjunto de objetos interage.

Promove o acoplamento fraco entre os objetos ao evitar que os objetos

explicitamente se refiram uns aos outros, permitindo que se varie

independentemente as interações.

Motivação

Em projetos orientados a objetos, é normal distribuir o comportamento entre

várias classes.

Isso pode resultar numa estrutura com muitas conexões entre os objetos e gera

a necessidade de que cada objeto conheça os demais.

Por exemplo:

Objetos da classe ClienteDoBanco, em geral, interagem com objetos da classe

FundoDeInvestimentosMonetatios. Mas não queremos que a classe

(49)

Padrões de Projeto - Cristiano Biancardi

Define um objeto que encapsula a

informação de como um conjunto de

outros objetos interagem entre si.

Promove o acoplamento fraco:

permitindo que você altere a forma de interação

(50)
(51)
(52)

Memento

Memento

Usado para restaurar o estado de um

objeto.

Problema:

É preciso guardar informações sobre um objeto

suficientes para desfazer uma operação

(53)
(54)

Um memento é um pequeno repositório para

guardar estado dos objetos

Pode-se usar outro objeto, um string, um arquivo.

Memento guarda um snapshot no estado interno

de outro objeto - a Fonte

Um mecanismo de Undo irá requisitar um memento da

fonte quando ele necessitar verificar o estado desse

objeto.

Só a fonte tem permissão para recuperar informações

(55)

Padrões de Projeto - Cristiano Biancardi

(56)

Exemplo:

Cada vez que um objeto for criado ou movido, o sistema criará um

memento do objeto e o guardará em uma pilha.

Cada vez que o usuário clicar no botão Undo, o código irá recuperar

o memento mais recente e restaurar a simulação ao estado

armazenado no topo da pilha.

public class Fonte {

private Memento memento;

private Object estado;

public Memento criarMemento() {

return new Memento();

}

public void setMemento(Memento m) {

memento = m;

public class Memento {

private Object estado;

Memento() { }

void setEstado(Object estado) {

this.estado = estado;

}

Object getEstado() {

return estado;

(57)

Padrões de Projeto - Cristiano Biancardi

Template Method

Template Method

Gabarito

Defini o esqueleto de um algoritmo numa classe,

delegando alguns passos às subclasses.

Permite que as subclasses alterem partes do

algoritmo, sem mudar sua estrutura geral.

Quando usar?

Quando a estrutura fixa de um algoritmo puder ser

definida pela superclasse deixando certas partes para

serem preenchidos por implementações que podem

variar

(58)
(59)

Padrões de Projeto - Cristiano Biancardi

(60)
(61)

Padrões de Projeto - Cristiano Biancardi

Outro Exemplo:

O método Arrays.sort (java.util) é um bom

exemplo de Template Method.

Ele recebe como parâmetro um objeto do tipo

Comparator que implementa um método

compare(a, b) e utiliza-o para definir as regras

de ordenação.

(62)
(63)

Padrões de Projeto - Cristiano Biancardi

State

State

Estado

O estado de um objeto, é uma combinação de

valores atuais de seus atributos.

Em tempo de execução, os valores destes

atributos podem variar de acordo com a

execução dos métodos do próprio objeto, ou via

métodos set.

O padrão é usado para permitir que um objeto

altere o seu comportamento quando o seu

estado muda.

(64)

Problema:

Algoritmos muitos grandes para representar as transições de

estado.

Objetivo:

usar objetos para representar estados e polimorfismo para

tornar a execução de tarefas dependentes de estado

transparentes.

(65)

Padrões de Projeto - Cristiano Biancardi

Estrutura

Contexto: define a interface de interesse aos clientes e mantém uma

instância de um EstadoConcreto que define o estado atual.

Estado: define uma interface para encapsular o comportamento

associado com um estado particular do contexto.

EstadoConcreto: Implementa um comportamento associado ao estado

(66)

Exemplo:

Estados de uma porta.

A porta funciona com um botão que alterna os estados de aberta,

(67)
(68)
(69)

Padrões de Projeto - Cristiano Biancardi

Strategy

Strategy

Estratégia

Definir uma família de algoritmos,

encapsular cada um, e fazê-los

intercambiáveis.

Permite que algoritmos mudem

independentemente entre clientes que os

utilizam.

(70)

Problema:

Várias estratégias, escolhidas de acordo com

(71)

Padrões de Projeto - Cristiano Biancardi

Idêntico a state na implementação.

(72)

Estrutura

Strategy: Define uma interface comum para todos os algoritmos

suportados

ConcreteStrategy: Implementa o algoritmo usando a interface de

Strategy

Context: Defini uma interface que permite a Strategy acessar seus

(73)
(74)

Command

Command

Encapsular uma requisição como um

objeto, permitindo que os clientes

parametrizem diferentes requisições, filas

ou fazer o registro de log de requisições.

Dar suporte operações que podem ser

(75)

Padrões de Projeto - Cristiano Biancardi

Motivação:

As vezes precisamos executar uma operação sem se

preocupar com qual objeto que vai realizá-la ou

simplesmente não conhecemos qual objeto vai receber

a delegação para executar tal operação.

Exemplo 1:

Em uma aplicação Cliente/Servidor geralmente temos o

componente Menu que é composto de vários itens. Cada

item do menu equivale uma operação, como salvar um

arquivo, ler arquivo, apagar arquivo, selecionar a paleta

de cores e etc..

Quando selecionamos um item do menu uma operação deve

ser realizada. Esta operação pode ser encapsulada em um

objeto, assim reduziremos o acoplamento entre o objeto menu

e o objeto que executa a operação.

(76)
(77)

Padrões de Projeto - Cristiano Biancardi

(78)
(79)

Padrões de Projeto - Cristiano Biancardi

Suporte para desfazer operações:

A operação "execute" do Command, pode armazenar

estados para reverter seus efeitos no próprio

comando.

Basta acrescentar na interface Command uma

operação chamada "Unexecute", que terá a

responsabilidade de desfazer a operação realizada

pelo "execute".

Os comandos realizados podem ser armazenados

(80)

Iterador

Iterador

Prover uma maneira de acessar os

elementos de um objeto agregado

,seqüencialmente, sem expor sua

representação interna.

Assim, oferece uma interface uniforme

para atravessar diferentes estruturas

agregadas.

(81)

Padrões de Projeto - Cristiano Biancardi

(82)
(83)

Padrões de Projeto - Cristiano Biancardi

(84)

Em Java:

Iterators são implementados nas coleções do

Java. É obtido através do método iterator() de

Collection, que devolve uma instância de

java.util.Iterator.

(85)

Padrões de Projeto - Cristiano Biancardi

(86)

Interpreter

Interpreter

Interpretador.

Propósito: interpretar expressões escritas em uma

gramática formal.

Eficiência não é um fator crítico.

"Dada uma linguagem, definir uma representação para

sua gramática junto com um interpretador que usa a

representação para interpretar sentenças na linguagem.“

Deve-se utilizar o padrão interpreter sempre que for

possível representar sentenças em árvores sintáticas.

Uso:

Implementação de compiladores

(87)

Padrões de Projeto - Cristiano Biancardi

(88)

AbstractExpression

Fornece a interface comum a todos os nós da árvore sintática.

TerminalExpression

Implementa a operação de interpretação para os símbolos terminais

NonterminalExpression

Implementa a operação de interpretação para os símbolos

nãoterminais.

A operação de interpretação é chamada recursivamente e a base da

recurssão é um símbolo terminal.

Contexto

contém informação que é global ao interpretador tal como valor das

variáveis para uma instância do problema e resultado das operações

realizadas

Cliente

(89)

Padrões de Projeto - Cristiano Biancardi

Exemplo:

Analisando uma expressão algébrica.

Regra Gramatical:

expressão = literal | somar | subtrair | expressão

Instância do problema:

subtrair(somar(subtrair(x,y),z),a)

onde x = 5, y = 2, z = 3 e a = 4

(90)
(91)
(92)
(93)
(94)
(95)
(96)

Visitor

Visitor

Visitante

Representar uma operação a ser

realizada sobre os elementos de uma

estrutura de objetos.

Permite definir uma nova operação sem

(97)

Padrões de Projeto - Cristiano Biancardi

Exemplo Visitor:

Não foi necessário mudar Grafico,

alterando o nome do método na

Classe: gerarPNG para gerarHTML.

(98)

Padrões Criacionais

Singleton

Prototype

Builder

Factory

Abstract Factory

(99)

Padrões de Projeto - Cristiano Biancardi

Singleton

Singleton

Intenção:

Garantir que uma classe tenha somente uma

instância e fornecer um ponto global de acesso

à mesma.

Motivação

Em muitas situações é necessário garantir que

algumas classes tenham uma e somente uma

instância.

Exemplo: o gerenciador de arquivos num sistema

deve ser único; escalonadores; gerenciadores de

janelas.

(100)
(101)

Padrões de Projeto - Cristiano Biancardi

Como assegurar que haja uma única instância?

Uma forma é de não permitir chamadas ao construtor

public class ConexaoDB {

private static ConexaoDB myInstance = null;

private Connection conn = null; private String user; private String password;

private String db; private String port; private static String IP;

private ConexaoDB() {

try {

Class.forName("oracle.jdbc.OracleDriver");

conn = DriverManager.getConnection("jdbc:oracle:thin:" + user

+ "/" + password + "@" + IP + ":" + port + ":" + db);

} catch (SQLException sqle) {

sqle.printStackTrace();

} catch (ClassNotFoundException cnfe) {

cnfe.printStackTrace();

} // try

}

public synchronized static ConexaoDB getInstance() {

if (conn == null) conn = new ConexaoDB();

return conn;

}

public Connection getConection(){

return conn;

}

}

(102)

Prototype

Prototype

Protótipo

Tem como objetivo criar objetos

específicos a partir da instância de um

protótipo.

Isso permite criar novos objetos através da

cópia deste protótipo.

Um cliente solicita um protótipo e este clona a

si próprio.

(103)

Padrões de Projeto - Cristiano Biancardi

Problema:

Criar um objeto novo, mas aproveitar o estado

(104)

Estrutura:

Cliente – solicita a um protótipo que crie

uma cópia de si mesmo, gerando outro

objeto.

Prototype – específica uma interface para

clonar a si próprio.

Concrete Prototype – implementa uma

(105)
(106)

Prototype em Java

Se o objeto apenas contiver tipos primitivos em

seus campos de dados, é preciso

declarar que a classe implementa Cloneable

sobrepor clone() da seguinte forma:

public Object clone() {

try {

return super.clone();

(107)

Padrões de Projeto - Cristiano Biancardi

Se o objeto contiver campos de dados que são

referências a objetos, é preciso fazer cópias

desses objetos também.

public class Circulo implements Cloneable{

private Point origem;

private double raio;

public Object clone() {

try {

Circulo c = (Circulo)super.clone();

c.origem = origem.clone(); // Point deve ser clonável!

return c;

} catch (CloneNotSupportedException e) {return null;}

}

(108)

Observação:

O padrão Prototype permite que um cliente crie

novos objetos ao copiar objetos existentes

Uma vantagem de criar objetos deste modo é poder

aproveitar o estado existente de um objeto

Em Java: preciso lembrar que ele só faz cópias

rasas: é preciso copiar também cada objeto membro

e seus campos recursivamente.

(109)

Padrões de Projeto - Cristiano Biancardi

Builder

Builder

Separar a construção de um objeto

complexo de sua representação para que

o mesmo processo de construção possa

criar representações diferentes.

Move a lógica de construção para um

objeto fora da classe a ser instanciada.

Razões: reduzir o tamanho de uma classe que

tem muitos métodos e também permitir a

(110)
(111)
(112)

Colaborações

O Cliente cria o objeto Diretor e o configura

com o Builder desejado.

O Diretor notifica o Builder sempre que uma

parte do produto deve ser construída

Builder trata solicitações e acrescenta partes

ao produto

(113)

Padrões de Projeto - Cristiano Biancardi

Exemplo:

aplicação que converte o formato

RTF

para uma série de outros

formatos

e que permite a inclusão de suporte para conversão para outros

formatos, sem a alteração do código fonte do leitor de RTF.

A implementação da solução:

realizada através de uma classe de leitura (director) associada a uma

classe capaz de converter o formato RTF para outra representação

(builder).

o objeto da classe de leitura lê cada

token

do texto e executa o método

apropriado no objeto de conversão, de acordo com tipo do token.

a classe de conversão possui um método para cada tipo de token,

incluindo os

caracteres

comuns, parágrafos, fontes e etc.

Para cada formato de texto suportado é criada uma classe de

conversão especializada (concrete builder).

Um conversor para formato

ASCII

, por exemplo, poderia ignorar

qualquer requisição para converter tokens que não fossem

caracteres comuns.

Um conversor para o formato

PDF

, por outro lado, iria processar

(114)
(115)

Padrões de Projeto - Cristiano Biancardi

abstract class ConversorTexto {

public void converterCaractere(char c) {}

public void converterParagrafo() {}

public void converterFonte(Fonte f) {}

}

class ConversorPDF extends ConversorTexto {

public void converterCaractere(char c) {

System.out.print("Caractere PDF");

}

public void converterParagrafo() {

System.out.print("Parágrafo PDF");

}

public void converterFonte(Fonte f) {

System.out.print("Fonte PDF");

}

}

class ConversorTeX extends ConversorTexto {

public void converterCaractere(char c) {

System.out.print("Caractere Tex");

}

public void converterParagrafo() {

System.out.print("Paragrafo Tex");

}

public void converterFonte(Fonte f) {

System.out.print("Fonte Tex");

}

}

class ConversorASCII extends ConversorTexto {

public void converterCaractere(char c) {

System.out.print("Caractere ASCII");

}

(116)

class LeitorRTF {

private ConversorTexto conversor;

LeitorRTF(ConversorTexto c) {

this.conversor = c;

}

public void lerRTF() {

List<Token> tokens = obterTokensDoTexto();

for (Token t : tokens) {

if (t.getTipo() == Token.Tipo.CARACTERE) {

conversor.converterCaractere(t.getCaractere());

}

if (t.getTipo() == Token.Tipo.PARAGRAFO) {

conversor.converterParagrafo();

}

if (t.getTipo() == Token.Tipo.FONTE) {

conversor.converterFonte(t.getFonte());

}

}

}

}

public class Cliente {

public static void main(String[] args) {

ConversorTexto conversor;

if (args[0].equals("pdf")) {

conversor = new ConversorPDF();

} else if (args[0].equals("tex")) {

conversor = new ConversorTeX();

} else { conversor = new ConversorASCII(); }

LeitorRTF leitor = new LeitorRTF(conversor);

(117)
(118)

Factory Method

Factory Method

Define uma interface para criar um objeto mas deixa que

subclasses decidam que classe instanciar.

Permite que uma classe delegue a responsabilidade de

instanciação às subclasses.

Usado:

em casos em que o cliente não consegue antecipar a classe de

objetos que deve criar.

O Factory Method decide com base do ‘contexto’, qual das

subclasses ativar.

Um exemplo simples: leitura de objetos serializados num arquivo.

ou quando uma classe quer que suas subclasses especifiquem

(119)

Padrões de Projeto - Cristiano Biancardi

(120)
(121)

Padrões de Projeto - Cristiano Biancardi

//Esta classe abstrata é a Factory que retorna

//instancia de outras factories.

abstract class DAOFactory {

public abstract UserDAO getUserDAO();

public static DAOFactory getInstance(int whichFactory) {

switch (whichFactory) {

case 1:

return new MySqlUserDAOFactory();

case 2:

return new PostgresUserDAOFactory();

default:

return null;

}

}

}

//Factory para MySql

class MySqlUserDAOFactory extends DAOFactory {

@Override

public UserDAO getUserDAO() {

return new MySqlUserDAO();

}

}

//Factory para Postgres

class PostgresUserDAOFactory extends DAOFactory {

@Override

public UserDAO getUserDAO() {

return new PostgresUserDAO();

}

(122)

interface UserDAO {

public void save(Object o);

public void update(Object o);

//outros

}

class MySqlUserDAO implements UserDAO {

public void save(Object o) {}

public void update(Object o) {}

}

class PostgresUserDAO implements UserDAO {

public void save(Object o) {}

public void update(Object o) {}

}

//Vamos ver como chamariamos as nossas classes:

public class DemoFactoryMethod{

public static void main(String[] args) {

DAOFactory daoFactory = DAOFactory.getInstance(1);

// retorna a factory para MySql

UserDAO userDAO = daoFactory.getUserDAO();

userDAO.save(new Object());

DAOFactory daoFactory2 = DAOFactory.getInstance(2);

// retorna a factory para Postgres

(123)
(124)
(125)
(126)

01 public class FactoryExample {

02 public static void main( String args[] ) {

03 //parâmetro passado como argumento no console

04 //pega a instância do tipo do carro

05 Carro carro = CarroFactory.getCarro( args[0] );

06 //mostra o valor

07 if( carro != null ) {

08 System.out.println( "Preço: " + carro.getPreco() );

09 }

10 }

11 }

(127)

Padrões de Projeto - Cristiano Biancardi

Abstract Factory

Abstract Factory

Intenção: fornecer uma interface para a

criação de famílias de objetos relacionados

ou dependentes sem especificar suas

classes completas

Aplicável a situações nas quais o sistema

deve ser independente de como seus

produtos são criados, compostos ou

representados

o sistema deve ser configurado como um

(128)
(129)
(130)

01 public abstract class Fabricante {

02 protected String name;

03

04 public abstract Carro getCarro( String marca );

05

06 public static Fabricante getInstance( String fabricante ) {

07 if( fabricante == null ) {

08 return null;

09 }

10 else if(fabricante.equals("Chevrolet")) {

11 return new Chevrolet();

12 }

13 else if(fabricante.equals("Volkswagen")) {

14 return new Volkswagen();

15 }

16 else {

17 return null;

18 }

19 }

20 }

22 public class Chevrolet extends Fabricante {

23 public Chevrolet() {

24 name = "Chevrolet";

25 }

27 public Carro getCarro( String marca ) {

28 if( marca == null ) { return null; }

31 else if( marca.equals("Vectra") ) {

32 return new Vectra(); }

34 else if( marca.equals("Omega") ) {

35 return new Omega(); }

(131)

Padrões de Projeto - Cristiano Biancardi

01 public class AbstractFactoryExample {

02 public static void main( String args[] ) {

03 //parâmetro passado como argumento no console

04 //pega a instância do fabricante

05 Fabricante fab = Fabricante.getInstance( args[0] );

06 //pega a instância do carro, de acordo com o fabricante

07 Carro carro = fab.getCarro( args[1] );

08 //mostra o valor

09 if( carro != null ) {

10 System.out.println( "Preço: " + carro.getPreco() );

11 }

12 }

13 }

43 public class Volkswagen extends Fabricante {

44 public Volkswagen() {

45 name = "Volkswagen"; }

48 public Carro getCarro( String marca ) {

49 if( marca == null ) {

50 return null; }

52 else if( marca.equals("Gol") ) {

53 return new Gol(); }

55 else if( marca.equals("Golf") ) {

56 return new Golf(); }

58 else { return null; }

61 }

(132)

Outros

Outros

MVC

Um dos primeiros padrões identificados na área

de software foi o modelo MVC:

model,

view,

controller

Que foi usado no projeto da interface de

(133)

Padrões de Projeto - Cristiano Biancardi

Model: responsável pelo armazenamento e manutenção

dos dados utilizados pela aplicação.

Modelo de classes proveniente da fase de análise

View: é a camada responsável pela interface com o

usuário.

Controller: é a camada responsável pelo tratamento de

eventos e implementação das regras de negócio

normalmente implicam em mudanças nos dados através dos

serviços de model.

um grupo de classes que controla, ou sincroniza, o

(134)

Motivação Inicial:

Mesmo modelo com diferentes visões!

Interface texto

Interface Desktop

Interface Web ...

(135)

Padrões de Projeto - Cristiano Biancardi

Funcionamento:

A visão

Parte usada para transformar e preparar os dados do

modelo para que possam ser apresentados de alguma

forma (HTML, swing etc).

O controlador retira os dados do modelo e os entrega

para a visão (ou retira dados da interface e alimenta o

modelo).

Esta, por sua vez, alimenta templates com estes dados

para que possam ser apresentados ao usuário.

Além disso, efetua-se algum tratamento do tipo:

Verificação de campos obrigatórios

(136)

O modelo

Parte que encapsula os dados da aplicação.

Fornecer rotinas para administrar e manipular dados.

Deve conter métodos para adicionar, eliminar e atualizar

informações dos objetos na base de dados.

Também deve conter métodos para obter a lista de objetos

existentes.

De modo geral, a técnica de acesso aos dados deve ser

encapsulada no modelo.

Desta forma, se uma aplicação for transferida de um sistema que

usa banco de dados para um sistema que usa arquivos texto para

guardar as informações, o único elemento que precisa ser alterado

será o modelo

(137)

Padrões de Projeto - Cristiano Biancardi

O controlador

Responsável pelas respostas às ações dos usuários.

No caso de uma aplicação desktop, uma ação de usuário

(geralmente) é a solicitação de uma consulta aos dados

de um cliente.

O controlador é acionado pela Visão e vai responder de

acordo, fazendo com que o Modelo manipule os dados

necessários (consulta o cliente no banco e monta o objeto

que o representa) para depois passá-los para a Visão

para que possam ser mostrados.

Representa a implementação dos casos de uso: fluxo

(138)

Por que o controlador é necessário?

Porque se a sua visão mudar, o impacto na aplicação

é pequeno.

O controlador diria o seguinte:

"Não me importa como o usuário vê o sistema,

coloque os dados em mim, e sinalizo ao modelo

que eu tenho novas informações para o

(139)

Padrões de Projeto - Cristiano Biancardi

Estrutura

Modelo

Visão

Controle

Comando/ações dos usuários

Invoca os métodos públicos

Invoca os métodos públicos para

pesquisa o estado do modelo

Estimula o sistema

(140)
(141)

Padrões de Projeto - Cristiano Biancardi

(142)

Vantagens

O mesmo modelo pode ser usado com diferentes visões (ou aplicações

diferentes).

Clareza e modularidade de projeto.

É possível ter desenvolvimento em paralelo para o modelo, visão e controle

pois são independentes.

Necessário apenas a definição da interface contratual a ser usada.

É muito simples incluir novos clientes apenas incluindo seus visões e

controles.

Desvantagens

Complexidade adicional, só justificável em aplicações de médio e grande

porte.

Não é aconselhável para pequenas aplicações.

Requer uma quantidade maior de tempo para analisar e modelar o sistema.

Requer pessoal especializado.

(143)

Padrões de Projeto - Cristiano Biancardi

Simulando uma consulta de cliente:

No formulário (visão), o campo código preenchidos e

validado.

No evento do clique do botão consultar, as informações do

formulário são passadas para um objeto (controlador), que

servirá de meio de transporte para os dados.

Nesse mesmo objeto controlador o modelo é manipulado e o

código é consultado no banco de dados.

Um objeto do tipo cliente é retornado pelo modelo ao

controlador que por sua vez repassa para a visão para que

os dados possam ser mostrados ou uma mensagem de

código não cadastrado seja exibida.

(144)

//Isso está no evento do clique do botão cadastrar

//verifica se código é valido

Cliente cli = Controlador. consCliente(tfdcod.getText());

if (cli != null) {

//td ocorreu bem

//Mostra os dados do cliente na tela

} else {

//algo deu errado

//Mostra uma mensagem de erro

}

public Cliente consCliente(String cod ) {

//Aqui o modelo é acessado

return Cliente.consulta();

}

class Cliente {

static Cliente consulta (String cod){

//consulta dados no banco

//se ok retorna o objeto;

Visão

Controle

(145)

Padrões de Projeto - Cristiano Biancardi

Referências:

Projeto de Software. Erick Braude. Porto Alegre. Bookman,

2005.

Padrões de Projeto em Java. Steven John Metsker.

Padrões de Projeto: soluções reutilizáveis de software

orientados a objetos. E. Gamma. Porto Alegre: Bookman,

2006.

Projeto de Sistemas: Notas de Aulas. Ricardo Falbo. UFES,

www.inf.ufes.br/~falbo

, 2003.

GoF Design Patterns em Java

. Argonavis.

Referências

Documentos relacionados

O Museu Digital dos Ex-votos, projeto acadêmico que objetiva apresentar os ex- votos do Brasil, não terá, evidentemente, a mesma dinâmica da sala de milagres, mas em

nhece a pretensão de Aristóteles de que haja uma ligação direta entre o dictum de omni et nullo e a validade dos silogismos perfeitos, mas a julga improcedente. Um dos

Equipamentos de emergência imediatamente acessíveis, com instruções de utilização. Assegurar-se que os lava- olhos e os chuveiros de segurança estejam próximos ao local de

Para Vilela, embora a locação de bens móveis não seja contrato de prestação de serviços (aquele que dá origem a uma obrigação de fazer, enquanto a locação gera a obrigação

A prova do ENADE/2011, aplicada aos estudantes da Área de Tecnologia em Redes de Computadores, com duração total de 4 horas, apresentou questões discursivas e de múltipla

O objetivo deste experimento foi avaliar o efeito de doses de extrato hidroalcoólico de mudas de tomate cultivar Perinha, Lycopersicon esculentum M., sobre

17 CORTE IDH. Caso Castañeda Gutman vs.. restrição ao lançamento de uma candidatura a cargo político pode demandar o enfrentamento de temas de ordem histórica, social e política

O enfermeiro, como integrante da equipe multidisciplinar em saúde, possui respaldo ético legal e técnico cientifico para atuar junto ao paciente portador de feridas, da avaliação