Subtype Polymorphism. Interfacce e subtype polimorfismo Tipi, sottotipi e conversioni di tipo Polimorfismo e dinamic dispatch.

Slides:



Advertisements
Presentazioni simili
Generazione dinamica di codice.NET 2.0 Ricci Gian Maria MarCamp : 24 febbraio 2007.
Advertisements

Classi ed Oggetti in JAVA
Fondamenti di Informatica
Costruttori e Distruttori
Universita di Camerino
Informatica 2 Lezione 4 Corso di laurea in matematica Informatica 2 Dott. Ing. Leonardo Vito Corso di laurea matematica indirizzo matematica per le applicazioni.
26/10/2004Laboratorio di Programmazione - Luca Tesei1 Variabili e Oggetti Lo spazio di memoria di Java Le API di Java.
Programmazione object oriented in C++
Differenze nei vari linguaggi di Elisa Trifirò e Barbara Tacchino
1 Semantica Operazionale di un frammento di Java: lo stato.
Classi ed Oggetti in Java (Cenni). Richiami Ruolo delle Classi in Java Oggetti.
Semantica Operazionale di un frammento di Java: lo stato
9/12/2004Laboratorio di Programmazione - Luca Tesei1 Ereditarietà
Dispatch.
Interfacce. Interfacce come strumento di progetto Scelta delle classi di un progetto Criteri di coesione e accoppiamento Interfacce e riuso di codice.
Package, Interfacce, Ereditarietà Dott. Ing. Leonardo Rigutini Dipartimento Ingegneria dellInformazione Università di Siena Via Roma 56 – – SIENA.
1 Programmazione ad oggetti in Java E.Mumolo, DEEI
Introduzione al linguaggio Java
Eliana minicozzi linguaggi L1 Lezione3.
eliana minicozzi linguaggi1a.a lezione2
1 Lezione XIII Lu 17-Nov-2005 Programmare le classi.
Overriding.
Gestione dei Progetti Software 2 (a.a. 2004/05) - Lezione 3 1 JAVA e Internet: il World Wide Web Internet: milioni di computer collegati fra di loro attraverso.
Ingegneria del software I
Gerarchia di classi Java
AA2003/04 © M.A. Alberti Programmazione Interfacce 1 Programmazione Corso di laurea in Informatica.
1 Le gerarchie di tipi. 2 Supertipi e sottotipi 4 un supertipo –class –interface 4 può avere più sottotipi –un sottotipo extends il supertipo ( class.
Puntatori - Cenni Nicola Fanizzi Corso di Programmazione C.d.L. in Informatica DIB - Università degli Studi di Bari.
Tipo di dato: collezione di valori omogenei ed effettivamente presentati, dotata di un insieme di operazioni che li manipolano – aiutano lorganizzazione.
1 laboratorio di calcolo II AA 2003/04 sesta settimana a cura di Domizia Orestano Dipartimento di Fisica Stanza tel. ( )
Ereditarietà. Concetti principali Ereditarietà e (overriding) di metodi Dynamic dispatch e polimorfismo Ereditarietà e costruttori Livelli di accesso.
Ereditarietà. Concetti principali Ereditarietà e (overriding) di metodi Dynamic dispatch e polimorfismo Ereditarietà e costruttori Livelli di accesso.
Classi. Progetto di classi: Dalla specifica dellinterfaccia, alla definizione dellimplementazione Metodi Costruttori Documentazione e commenti Variabili.
Contenuti del corso Programmazione ad Oggetti Oggetti, polimorfismo, ereditarieta Metodologie di progetto Astrazione ed incapsulamento ( encapsulation)
Programmazione con Interfacce
Capitolo 9 Interfacce e polimorfismo
Java base IV: Java e la programmazione O.O.
Le funzioni a tempo di esecuzione
CLASSI ED EREDITARIETÀ Come si è visto, è cruciale che la gerarchia rispecchi la realtà del mondo ma a volte ciò contraddice principi di efficienza Esempio:
IL TEMA DELLA RIUSABILITÀ Si vuole riusare tutto ciò che può essere riusato (componenti, codice, astrazioni) Non è utile né opportuno modificare codice.
IL TEMA DELLA RIUSABILITÀ Si vuole riusare tutto ciò che può essere riusato (componenti, codice, astrazioni) Non è utile né opportuno modificare codice.
Programmazione in Java (8)
Ereditarietà e Polimorfismo
Java Contardi Carlo A.S. 2008/09.
Introduzione alla programmazione Object Oriented
Enumerazioni e Classi 1. Enumerazioni Permettono di definire nuovi tipi che consistono in un insieme di valori costanti (ognuno con un nome) – Migliorano.
1 FONDAMENTI DI INFORMATICA II Ingegneria Gestionale a.a ° Ciclo Polimorfismo.
Fondamenti di Informatica II Ingegneria Informatica / Automatica (A-I) Meccanica Prof. M.T. PAZIENZA a.a – 3° ciclo.
30/11/2004Laboratorio di Programmazione - Luca Tesei1 Interfacce e Polimorfismo.
Ereditarieta’. Contenuti Introduciamo un meccanismo fondamentale di Java: l’ereditarieta’ Permette di estendere classi gia’ definite (ovvero di definire.
1 Osservazioni Generali Struttura di programma Gerarchia di classi: overloading, overriding, e dispatching Analisi ed esecuzione Modificabilità e condivisione.
Fondamenti di Informatica 2 Ingegneria Informatica Docente: Giovanni Macchia a.a
Fondamenti di Informatica II Ingegneria Informatica (A-I) Prof. M.T. PAZIENZA a.a – 3° ciclo.
Fondamenti di Informatica 2 Ingegneria Informatica Docente: Giovanni Macchia a.a
OBJECT ORIENTED DATABASE introduzione. OGGETTO Ha due componenti:  stato: valore di alcune variabili (variabili di istanza)  comportamento: insieme.
Fondamenti di informatica Oggetti e Java Luca Cabibbo Luca Cabibbo – Fondamenti di informatica: Oggetti e Java Copyright © 2004 – The McGraw-Hill Companies.
1 Principio di sostituzione Se un oggetto di tipo S può essere sostituito ovunque ci si aspetti un oggetto di tipo T, allora S è una sottoclasse corretta.
Ese 1 (del 31 Marzo 2004). Il compilatore Non esegue il programma, non guarda i valori che possono assumere di volta in volta le variabili, non fa assunzioni.
Programmazione in Java. Classi I programmi in Java consistono di classi. Le classi consentono di definire: collezioni di procedure (metodi statici) tipi.
Cose nuove di Java (prima a chiacchiera, poi formalmente)
LIP: 2 Maggio 2008 Classi Astratte. Cos’e’ una Classe Astratta una classe astratta e’ un particolare tipo di classe permette di fornire una implementazione.
Progettare una classe 21 Febbraio La classe BankAccount Vogliamo realizzare una classe i cui oggetti sono dei semplici conti bancari. * Identifichiamo.
Classi ed Oggetti in Java (Cenni). Richiami Cenni sull’ Implementazione, Macchine Astratte, Compilatore, Interprete Ruolo delle Classi in Java Oggetti.
LIP: 11 Maggio 2007 Classi Astratte. Cos’e’ una Classe Astratta una classe astratta e’ un particolare tipo di classe permette di fornire una implementazione.
Esercitazione del 9 marzo 2007 Ereditarieta’. Richiami Definire sottoclassi (ereditarieta’) Overriding Specificatori di accesso (private, protected) Principio.
Introduzione a Java. Java Linguaggio Object-Oriented La maggior parte dei dati manipolati dai programmi e’ contenuta in oggetti La principale forma di.
28/12/2001package 1 Package Pacchetti e interfacce.
Array di controlli.
Transcript della presentazione:

Subtype Polymorphism

Interfacce e subtype polimorfismo Tipi, sottotipi e conversioni di tipo Polimorfismo e dinamic dispatch

Conversioni di tipo Variabile: locazione con un tipo associato Tipo della variabile determinato dal compilatore guardando la dichiarazione Una variabile di tipo reference contiene un riferimento ad un oggetto Oggetto: istanza di una classe Tipo delloggetto: la classe che lo crea Determinato a run time Una variabile può assumere come valori riferimenti ad oggetti di classi diverse Continua…

Conversioni di tipo È possibile assegnare un riferimento di tipo classe ad una variabile di tipo interfaccia purchè la classe implementi linterfaccia BankAccount account = new BankAccount(10000); Measurable x = account; // OK Coin dime = new Coin(0.1, "dime"); Measurable y = dime; // OK Continua…

Conversioni di tipo La conversione è lecita solo in determinate situazioni Problema: Rectangle non implementa Measurable Measurable x = new Rectangle(5, 10, 20, 30); // ERRORE

Subtyping Subtyping (<:) Una relazione che permette di decidere quando è legittimo convertire un tipo riferimento in un altro Chi decide cosa/quando è legittimo? il compilatore! Per il momento la regola è: Continua… T1 <: T2 sse T1 è una classe, T2 è una interfaccia T1 implementa T2.

Subtyping Principio di sostituibilità Un riferimento di un sottotipo può essere usato ovunque ci si aspetti un riferimento di un supertipo Le regole di sottotipo devono garantire la correttezza del principio di sostituibilità Continua…

Subtyping La regola C <: I se C implementa I Principio di sostituibilità un riferimento di tipo C può sempre essere usato dove si attende un riferimento di tipo I E ragionevole perché se C implementa I, C definisce public tutti i metodi dichiarati da I Quindi tutti le invocazioni di metodo possibili per I sono supportate da C Continua…

Subtyping e regole di typing Regola di assegnamento Un riferimento di tipo T1 si puo sempre assegnare ad una variabile di tipo T2 sse T1 <: T2 Un riferimento di tipo classe può sempre essere assegnato ad una variabile di tipo interfaccia (se la classe implementa linterfaccia) Regola di passaggio di parametri Un riferimento di tipo T1 si puo sempre passare per un parametro di tipo T2 sse T1 <: T2 Un riferimento di tipo classe può sempre essere passato per un parametro di tipo interfaccia (se la classe implementa linterfaccia)

Domanda Data limplementazione generica della classe DataSet, che oggetti possiamo passare come argomento per x ? public class DataSet { public void add(Measurable x) {... }... }

Risposta Qualunque istanza di una una classe che implementa Measurable

Polimorfismo – dynamic dispatch Una variabile di tipo interfaccia ha sempre come valore un riferimento di una classe che implementa linterfaccia Continua… Measurable x; x = new BankAccount(10000); x = new Coin(0.1, "dime");

Polimorfismo – dynamic dispatch Possiamo invocare ognuno dei metodi dellinterfaccia: Quale metodo invoca? double m = x.getMeasure();

Polimorfismo – dynamic dispatch Dipende dal riferimento corrente memorizzato nella variabile Se x riferisce un BankAccount, invoca il metodo BankAccount.getMeasure() Se x riferisce un Coin, invoca il metodo Coin.getMeasure() Polimorfismo (molte forme): il comportamento varia, e dipende dal tipo dinamico della variabile Continua…

Domande 5.È impossibile costruire un oggetto di tipo Measurable. Perché? 6.Perché invece é possibile dichiarare una variabile di tipo Measurable ?

Risposte 5. Measurable è una interfaccia. Le interfacce non hanno campi o implementazione di metodo. 6.Perché Measurable è un tipo: la variabile non riferirà mai una istanza di Measurable, (le interfacce non hanno istanze) ma piuttosto oggetto di una qualche classe che implementa linterfaccia Measurable. Continua…

Costruiamo una applicazione per disegnare un insieme di forme geometriche contenute in una componente grafico: definiamo GWin, una classe che descrive un contenitore di forme geometriche disegnate mediante una invocazione del metodo paint() per esemplificare, consideriamo due tipi di forme: Car e Smiley Ancora un esempio

Forme grafiche class Car {... public void draw(Graphics2D g) { // Istruzioni per il disegno... } } class Smiley {... public void draw(Graphics2D g) { // Istruzioni per il disegno... } }

Un contenitore di Cars e Smileys GWin /** Una finestra che contiene un insieme Cars e Smileys */ class GWin { /** Disegna tutte le forme di questo component */ public void paint(){ /* disegna su g */ } /** Componente grafica su cui disegnare */ private Graphics2D g; }

Domanda Che struttura utilizziamo per memorizzare le forme contenute nella GWin ? Come definiamo il metodo paint() in modo che disegni tutte le forme della componente?

Risposte definiamo una nuova interfaccia: Shape Ridefiniamo le classi Car e Smiley in modo che implementino Shape Memorizziamo gli oggetti della componente in una ArrayList interface Shape { void draw(Graphics2D g); }

Car e Smiley implementano Shape class Car implements Shape {... public void draw(Graphics2D g) { // Istruzioni per il disegno... } } class Smiley implements Shape {... public void draw(Graphics2D g) { // Istruzioni per il disegno... } }

Mantiene una ArrayList GWin class GWin { private Graphics2D g; private ArrayList shapes; // crea una GWin con un insieme di forme public GWin(Shape... shapes) { Graphics2D g = new Graphics2D(); this.shapes = new ArrayList (); for (Shape s:shapes) this.shapes.add(s); } // disegna tutte le componenti della GWin public void paint() { for (Shape s:shapes) s.draw(g); }

Diagramma delle Classi Car GWin Smiley Shape Car

So long, for today

Polimorfismo – dynamic dispatch Dynamic dispatch : Il metodo da invocare per rispondere ad un messaggio è deciso a tempo di esecuzione

Dynamic dispatch in GWin class GWin {... private ArrayList shapes;... public void paint() { // disegna tutte le componenti della GWin // il metodo invocato effettivamente da ogni // messaggio s.draw(g) dipende dalla classe // di cui s è istanza ed è deciso a runtime for (Shape s:shapes) s.draw(g); }.... }

Dynamic dispatch vs overloading Dynamic dispatch : Il metodo da invocare per rispondere ad un messaggio è deciso a tempo di esecuzione Notiamo bene Il metodo da invocare è deciso a runtime il compilatore decide se esiste un metodo da invocare Overloading: Nel caso esista più di un metodo, il compilatore decide staticamente il tipo del metodo da invocare

Dynamic dispatch vs overloading interface I { public String m(boolean b); public String m(double d); } class A implements I { public String m(boolean b) { return A.m(boolean); } public String m(double d) { return A.m(double); } } class B implements I { public String m(boolean b) { return B.m(boolean); } public String m(double d) { return B.m(double); } }

Dynamic dispatch vs overloading class Client { public void static show(I x) { // tipo del metodo invocato = m(boolean) // deciso dal compilatore staticamente // metodo invocato deciso dinamicamente // in funzione del tipo dellargomento // passato per x System.out.println( x.m(false) ); }

Domanda Che cosa hanno in comune i meccanismi di overloading e di dynamic dispatch? In cosa sono diversi?

Entrambi i meccanismi contribuiscono a decidono quale metodo eseguire in risposta ad un messaggio, ma Nelloverloading scelta è relativa al tipo del metodo, ed è fatta in compilazione guardando il tipo dei parametri Nel dynamic dispatch la scelta è relativa al corpo del metodo, ed è fatta in esecuzione guardando il tipo delloggetto che riceve il messaggio Risposta

Subtyping e sostituibilità Principio di sostituibilità Un riferimento di un sottotipo può essere usato ovunque ci si aspetti un riferimento di un supertipo Le regole di sottotipo garantiscono la correttezza del principio di sostituibilità Tutti i metodi del supertipo devono essere implementati dal sottotipo Il sottotipi può avere anche altri metodi Continua…

Subtyping e perdita di informazione Principio di sostituibilità Un riferimento di un sottotipo può essere usato ovunque ci si aspetti un riferimento di un supertipo Può causare perdita di informazione nel contesto in cui ci aspettiamo il supertipo, non possiamo usare solo I metodi del supertipo perdiamo la possibilità di utilizzare gli eventuali metodi aggiuntivi del sottotipo Continua…

Car e Smiley implementano Shape class Smiley implements Shape {... public void draw(Graphics2D g){... } public String mood() {... } } class Car implements Shape {... public void draw(Graphics2D g){... } public String brand() {... } }

Subtyping e perdita di informazione Consideriamo public static void printBrand(List l) { for (Shape s : l) // stampa la marca di tutte le macchine di l // ??? } Continua…

Subtyping e perdita di informazione Certamente non possiamo fare così … public static void printBrand(List l) { for (Shape s : l) // stampa la marca di tutte le macchine di l System.out.println( s.brand() ); // TYPE ERROR! } Continua…

Cast Permette di modificare il tipo associato ad una espressione Un cast è permesso dal compilatore solo se applica conversioni tra tipi compatibili Compatibili = sottotipi (per il momento) Anche quando permesso dal compilatore, un cast può causare errore a run time Se s non è un Car errore a run time Continua… ((Car)s).brand()

Cast Tipo statico e tipo dinamico di una variabile tipo statico: quello dichiarato tipo dinamico: il tipo del riferimento assegnato alla variabile (T)var causa errore in compilazione se T non è compatibile con il tipo statico di var in esecuzione ( ClassCastException ) se T non è compatibile con il tipo dinamico di var Continua…

Cast OK: Car sottotipo di Shape Compila correttamente il tipo dichiarato di s è Shape Car e Shape sono compatibili Esegue correttamente s è un Car (il tipo dinamico di s è Car) Shape s = new Car(); Continua… Car c = (Car) s

Cast OK: Car sottotipo di Shape Compila correttamente il tipo dichiarato di s è Shape Smiley e Shape sono compatibili Errore a run time s non è uno Smiley Shape s = new Car(); Continua… Smiley c = (Smiley) s

Cast Attenzione anche qui … public static void printBrand(List l) { for (Shape s : l) // ClassCastException se s instance of Smiley System.out.println( ((Car)s.)brand() ); } Continua…

instanceof Permette di determinare il tipo dinamico di una variabile Quindi permette di evitare errori in esecuzione Esegue correttamente, perchè x è sicuramente un T x istanceof T è true solo se x ha tipo dinamico T if (x instanceof T) return (T) x

Cast Questo, finalmente, è corretto public static void printBrand(List l) { for (Shape s : l) if (s instanceof Car) System.out.println( ((Car)s.)brand() ); }

Domanda E se volessimo disegnare solo le Shape s che sono Car s?

Risposta // disegna tutte le Cars della GWin public void paint(){ for (Shape c:shapes) if (c instanceof Car) c.draw(g); }