Marco Faella I pattern Template Method e Factory Method

Documenti analoghi
Programmazione. Cognome... Nome... Matricola... Prova scritta del 11 luglio 2014

18 - Classi parzialmente definite: Classi Astratte e Interfacce

A. Lorenzi, A. Rizzi Java. Programmazione ad oggetti e applicazioni Android Istituto Italiano Edizioni Atlas

18 - Vettori. Programmazione e analisi di dati Modulo A: Programmazione in Java. Paolo Milazzo

Corso Linguaggi di programmazione II - Unina Esercitazione (prova intercorso)

19 - Eccezioni. Programmazione e analisi di dati Modulo A: Programmazione in Java. Paolo Milazzo

La classe java.lang.object

Polimorfismo parametrico vs polimorfismo per inclusione

16 - Ereditarietà, tipi e gerarchie

Programmazione. Cognome... Nome... Matricola... Prova scritta del 22 settembre Negli esercizi proposti si utilizzano le seguenti classi:

Fondamenti di Informatica T-1. Ereditarietà & Polimorfismo

Capitolo 9. Tipi enumerativi, tipi generici e interfacce. c 2005 Pearson Education Italia Capitolo 9-1 / 73

Corso di Algoritmi e Strutture dati Programmazione Object- Oriented in Java (Parte I)

Riassunto: cos è la OOP? classi astratte, interfacce, classi interne. Scaletta. Figura con area()? Figura senza area()? Stefano Mizzaro 1.

Progettazione del Software

Esercitazione. Docente Ing. Mariateresa Celardo

Fondamenti di Informatica T-1. Classi e metodi astratti

Linguaggi di programmazione II AA 2010/2011 Esercitazione 2

Uguaglianza e copia di oggetti

Programmazione orientata agli oggetti Classi astratte e interfacce

GESTIONE DEGLI ERRORI

Ereditarietà. Ereditarietà. Ereditarietà. Ereditarietà

Classi astratte e progettazione OOP Esempio: l enciclopedia degli animali. Esempio Animali

Attraversamento di un albero (binario)

QUEUE : considerazioni. QUEUE : considerazioni. QUEUE : esempio. QUEUE : esempio

Lezione 13 Classi interne

SOMMARIO DIAGRAMMI DELLE CLASSI E DEGLI OGGETTI INGEGNERIA DEL SOFTWARE. Introduzione. Proprietà e Operazioni. Proprietà e Operazioni

FONDAMENTI DI INFORMATICA C Linguaggio Java: Eccezioni

Gestione delle eccezioni

Ereditarietà e Polimorfismo

In questa lezione. Polimorfismo

Programmazione ad oggetti

Definizione di classi

Algoritmi e Strutture Dati. Tipo di dato astratto e Strutture dati elementari

Indice generale Introduzione...vii Parte I Concetti e costrutti fondamentali... 1 Capitolo 1 Introduzione al linguaggio... 3

Alberi binari ( 7.3)

Alberi Binario in Java

Progettazione! Progettazione! Progettazione! Progettazione!

Programmazione Java Struttura di una classe, Costruttore, Riferimento this

Metodi statici. Dichiarazione e chiamata di metodi statici

Classi astratte e progettazione OOP Esempio: l enciclopedia degli animali

Definizione di metodi in Java

Indice. Prefazione. 3 Oggetti e Java 53

Classi astratte e progettazione OOP Esempio: l enciclopedia degli animali. Esempio Animali

Fondamenti di Informatica I

Laboratorio di Programmazione 1 [Java]

RETI DI CALCOLATORI Linguaggio Java: Eccezioni

Esempio: Interfacce. Gioco Interfacce

Corso sul linguaggio Java

ESERCIZI JAVA. Esercizi sulle Interfacce. Esercizio 1:

Main System Monitor Keyboard

Programmazione Java Avanzata PATTERN

STRINGHE IN JAVA In Java, le stringhe non sono pezzi di memo-ria con dentro dei caratteri, come in C: sono oggetti appartenenti alla classe

Il pattern ABSTRACT FACTORY

Esempio: Interfacce. Gioco Interfacce

Laboratorio di Programmazione Lezione 2. Cristian Del Fabbro

Esempio 2: Subtyping

Programmazione con Java

Uso di metodi statici. Walter Didimo

Transcript:

Marco Faella I pattern Template Method e Factory Method 12 Lezione n. Parole chiave: Java Corso di Laurea: Informatica Insegnamento: Linguaggi di Programmazione II Email Docente: faella.didattica@gmail.com A.A. 2009-2010

Esercizio: corpi celesti Cominciamo questa lezione con un esercizio, che ci condurrà ad un nuovo design pattern Per un programma di astronomia, si implementino le tre classi Planet, Moon e Star, che rappresentano, rispettivamente, un pianeta, una luna (ovvero, un satellite naturale) ed una stella. A ciascuno di questi corpi celesti è associato un nome ed una massa. Quando si crea un oggetto pianeta o luna, bisogna anche specificare il corpo intorno al quale questo orbita. Le classi devono verificare che i pianeti orbitino intorno a una stella, e le lune intorno a dei pianeti. Il tentativo di violare queste regole porta ad un'eccezione. Si fornisca anche una classe (o interfaccia) Body che rappresenta un generico corpo celeste, ed è quindi una superclasse di tutte le precedenti. La classe Body dispone di un metodo satelliteiterator, che restituisce un iteratore sull'insieme di satelliti di questo corpo. La slide seguente mostra un esempio d'uso di queste classi.

Esercizio: corpi celesti Le classi descritte nella slide precedente devono poter essere utilizzate nel modo seguente i dati astronomici sono tratti da www.wikipedia.org Body b[] = new Body[5]; b[0] = new Star("Sole", 1.98e30); // Marte orbita intorno al sole b[1] = new Planet("Marte", 6.14e23, b[0]); // Phobos e Deimos orbitano intorno a Marte b[2] = new Moon("Phobos", 1.07e16, b[1]); b[3] = new Moon("Deimos", 2.24e15, b[1]); java.util.iterator i = b[1].satelliteiterator(); System.out.println(" Lune di Marte: "); while (i.hasnext()) { Moon m = (Moon) i.next(); System.out.println(m.getName() + " : " + m.getmass()); System.out.println(" ed ora..."); b[4] = new Moon("Giove", 1, b[0]);

Esercizio: corpi celesti Il codice della slide precedente dovrebbe avere un output simile al seguente Lune di Marte: Phobos : 1.07E16 Deimos : 2.24E15 ed ora... Exception in thread "main" planets.body$invalidbodytypeexception at planets.body.addsatellite(body.java:32) at planets.body.<init>(body.java:17) at planets.moon.<init>(moon.java:6) at PianetiTest.main(PianetiTest.java:24) Ovvero, l'iteratore restituito dal metodo satelliteiterator permette di ottenere, una alla volta, le due lune di Marte L'ultima istruzione, che tenta di definire Giove come una luna del sole, fallisce lanciando un'eccezione, perché una luna non può orbitare direttamente intorno ad una stella

Esercizio: soluzione di massima Abbozziamo una soluzione dell'esercizio, con particolare riferimento al controllo necessario ad assicurare che lune e pianeti orbitino intorno a corpi del tipo giusto Cercheremo di seguire il principio secondo il quale bisogna raccogliere nelle superclassi (in questo caso, Body) il maggior numero possibile di funzionalità comuni Decidiamo quindi di introdurre in Body un metodo di supporto, chiamato isvalidsatellite, che prende un corpo celeste x come argomento, e restituisce vero se e solo se questo corpo potrebbe orbitare intorno ad x Body sarà una classe astratta perché non ha senso in questo contesto istanziare un corpo celeste generico Questo ci dà l'occasione di lasciare il metodo isvalidsatellite astratto, in modo che ciascuna sottoclasse lo ridefinisca nel modo appropriato Le prossime slide presentano una possibile implementazione della classe Body

Esercizio: la classe Body, prima parte public abstract class Body { private double mass; private String name; private Body parent; private List satellites; public Body(String name, double mass, Body parent) { this.name = name; this.mass = mass; this.parent = parent; satellites = new LinkedList(); if (parent!= null) parent.addsatellite(this); /** Controlla che un corpo sia del tipo giusto per essere un satellite di this. */ protected abstract boolean isvalidsatellite(body other); /** Lanciata quando si tenta di far orbitare un corpo intorno ad un altro corpo del tipo sbagliato. */ public static class InvalidBodyTypeException extends RuntimeException { ;

Esercizio: la classe Body, seconda parte /** Restituisce un iteratore sui corpi che orbitano intorno a questo corpo. */ public Iterator satelliteiterator() { return satellites.iterator(); /** Aggiunge un satellite a questo corpo. Chiamato solo dalle sottoclassi. */ protected void addsatellite(body other) { if ( isvalidsatellite(other) ) satellites.add(other); else throw new InvalidBodyTypeException();

Esercizio: la classe Planet Riportiamo una possibile implementazione della classe Planet Grazie ad una accurata pianificazione delle responsabilità, siamo riusciti a ridurre al minimo il codice contenuto nelle sottoclassi come Planet L'annotazione @Override indica che il metodo che segue intende eseguire l'overriding di uno della superclasse le annotazioni verranno illustrate in una lezione successiva public class Planet extends Body { public Planet(String name, double mass, Body parent) { super(name, mass, parent); @Override protected boolean isvalidsatellite(body other) { // Satellites of planets must be moons. return other instanceof Moon;

Il pattern TEMPLATE METHOD Contesto: 1) Un algoritmo è applicabile a più tipi di dati 2) L'algoritmo può essere scomposto in operazioni primitive. Le operazioni primitive possono essere diverse per ciascun tipo di dato 3) L'ordine di applicazione delle operazioni primitive non dipende dal tipo di dato Soluzione: 4) Definire una superclasse che abbia un metodo che realizza l'algoritmo e un metodo per ogni operazione primitiva 5) Le operazioni primitive non sono implementate nella superclasse (metodi astratti), oppure sono implementate in modo generico 6) Ridefinire in ogni sottoclasse i metodi che rappresentano operazioni primitive, ma non il metodo che rappresenta l'algoritmo

Diagramma del pattern TEMPLATE METHOD Il diagramma a destra illustra graficamente le classi coinvolte nel pattern TEMPLATE METHOD Vi si trova la superclasse, con metodi primitivi e metodo composito algorithm, e una sottoclasse, che ridefinisce appropriatamente i metodi primitivi Con riferimento all'esercizio dei corpi celesti: la classe Body rappresenta la superclasse il metodo addsatellite rappresenta algorithm il metodo isvalidsatellite è il metodo primitivo le classi Planet, Moon e Star sono le sottoclassi concrete di Body Figura 1: Diagramma UML tipico del pattern TEMPLATE METHOD.

Il pattern FACTORY METHOD Contesto: 1) Un tipo (creatore) crea oggetti di un altro tipo (prodotto) 2) Le sottoclassi del tipo creatore devono creare prodotti di tipi diversi 3) I clienti non hanno bisogno di sapere il tipo esatto dei prodotti Soluzione: 1) Definire un tipo per un creatore generico 2) Definire un tipo per un prodotto generico 3) Nel tipo creatore generico, definire un metodo (detto appunto metodo fabbrica) che restituisce un prodotto generico 4) Ogni sottoclasse concreta del tipo creatore generico realizza il metodo fabbrica in modo che restituisca un prodotto concreto

Diagramma del pattern FACTORY METHOD Il diagramma a destra illustra i rapporti tra le classi coinvolte nel pattern FACTORY METHOD Le due interfacce Creator e Product rappresentano il creatore generico e il prodotto generico, rispettivamente La relazione di dipendenza tra Creator e Product è dovuta semplicemente al fatto che il creatore ha un metodo (il metodo fabbrica, per l'appunto) che restituisce un oggetto di tipo Product Al di sotto, troviamo un creatore concreto e un prodotto concreto Naturalmente, la relazione di dipendenza si estende anche a loro Figura 2: Diagramma UML tipico del pattern FACTORY METHOD.

Applicazione del pattern FACTORY METHOD Il diagramma a destra illustra come il pattern FACTORY METHOD si ritrova applicato nella creazione di iteratori da parte delle collezioni come LinkedList Come si vede, Iterable rappresenta il creatore generico e Iterator il prodotto generico Un produttore generico è rappresentato dalla classe LinkedList, che implementa Iterable La classe LinkedList costruisce internamente un iteratore concreto, di una classe che non è documentata nella libreria standard, e che nel diagramma viene chiamata ConcreteIterator è probabile che questa sia una classe interna privata di LinkedList Figura 3: Diagramma dell'applicazione del pattern FACTORY METHOD alla creazione di iteratori da parte di collezioni della libreria standard.

Esempio negativo di FACTORY METHOD E' utile considerare esempi di progettazione che assomigliano al pattern FACTORY METHOD, ma che in realtà non gli corrispondono Ad esempio, consideriamo il metodo tostring della classe Object Non c'è un'interfaccia che rappresenti il creatore generico, però la classe Object potrebbe farne le veci Allo stesso modo, la classe String potrebbe fungere da prodotto generico Tuttavia, la classe String è final, cioè non è estendibile Quindi, manca uno dei presupposti principali del pattern, ovvero: Le sottoclassi del tipo creatore devono creare prodotti di tipi diversi Esercizio: esaminare la documentazione del metodo createetchedborder della classe javax.swing.borderfactory e stabilire se si tratta di un esempio del pattern FACTORY METHOD