28/12/2001package 1 Package Pacchetti e interfacce
28/12/2001 package2 Package Più classi o interfacce interrelate possono essere riunite in un package, dotato di nome Esempio: c e b d a MyPackage classe o interfaccia
28/12/2001 package3 Nomi di classi Il nome di una classe va sempre qualificato con il nome del package a cui appartiene, tranne quando viene usato all’interno dello stesso package Esempio: aaa.bbb.ccc.MyClass all’interno di aaa.bbb.ccc basta MyClass
28/12/2001 package4 Nomi di package Il nome di un package può essere composto da più identificatori separati da “.”: luca.utilities.internet Per evitare che package di produttori diversi abbiano lo stesso nome, si suggerisce di far iniziare il nome del package con il dominio Internet del produttore (invertito, e con il nome di più alto livello tutto maiuscolo): IT.unipv.vision.luca.utilities.internet
28/12/2001 package5 Pacchetti standard java.langclassi base del linguaggio Object, Thread, Throwable, System, String, Math, wrapper classes, …) java.ioclassi di I/O FileInputStream, FileOutputStream java.utilclassi di utilità Date, Random, … java.netclassi di supporto alle applicazioni di rete (socket, URL, …) java.appletclasse Applet, … java.awtAbstract Windowing Toolkit
28/12/2001 package6 L’istruzione package Specifica che le classi che seguono appartengono a un certo package Deve apparire all’inizio di una unità di compilazione Esempio: class a {.. class b {... class c {.. a.java package p; le classi a,b,c appartengono al package p Se lo statement è omesso, la classe appartiene al package anonimo
28/12/2001 package7 L’istruzione import Per evitare di usare sempre nomi completi di classi, si può usare lo statement import Esempio: import java.util.Date; class MyClass {class MyClass { java.util.Date today; Date today; …...} Note: import java.util.* importa tutte le classi del package java.util java.lang.* è sempre importato implicitamente
28/12/2001 package8 Package e directory Molti ambienti Java mappano i nomi dei package sui pathname del file system Esempio: aaa.bbb.ccc.MyClassaaa/bbb/ccc/MyClass.class packageclasse directories file pathname
28/12/2001 package9 CLASSPATH Per indicare al class loader da quale directory partire per la mappatura può essere usata la variabile di ambiente CLASSPATH Esempio (Unix): setenv CLASSPATH /classi : /usr/luca/classi :.
28/12/2001 package10 Visibilità Classi e interfacce sono visibili all’interno del package in cui sono dichiarate; sono visibili all’esterno del package solo se dichiarate public public class a { … public interface b { … Membri (campi e metodi) sono visibili quando: la loro classe è visibile e il loro modificatore li rende visibili
28/12/2001 package11 Visibilità di campi e metodi ModificatoreVisibilità private solo nella classe in cui è definito nessuno (default)solo nelle classi del package protected classi nel package e sottoclassi public tutte le classi NB: I membri di una interfaccia sono sempre pubblici più visibile
28/12/2001 package12 class a {... package pac esempio class b { private int i; private void m( ) {…} int j; void n( ) {…} public int k; public p( ){…} protected int i; protected void m( ){…} class d extends b {... package pac; class c {... class e extends d {... class d extends b {... visibile
28/12/2001 package13 Progettare la Visibilità Quando progettiamo una classe dobbiamo pensare a due tipi di utenti: quelli che utilizzeranno la classe per realizzare delle applicazioni quelli che estenderanno la classe per realizzare sottoclassi I primi useranno i membri public ; i secondi anche i membri protected Le interfacce public e protected vanno progettate con cura
28/12/2001 package14 package pac USA ESTENDE interfaccia DUE TIPI DI UTENTI class a { private int i; private void m( ) {…} int j; void n( ) {…} public int k; public p( ){…} protected int i; protected void m( ){…}
28/12/2001 package15 Package: riassunto I package: permettono di creare gruppi di classi e interfacce fra loro in relazione definiscono uno spazio di nomi locale per classi e interfacce evitando conflitti con classi e interfacce di altri package permettono di avere classi, interfacce e membri (campi e metodi) non visibili all’esterno del package possono essere organizzati gerarchicamente
28/12/2001 package16 Interfacce Un’interfaccia è un insieme di definizioni di metodi (senza implementazione) e (eventualmente) di dichiarazioni di costanti Definizione di una interfaccia: interface { corpo dell’interfaccia }
28/12/2001 package17 Interfacce, se specificato, deve valere public ; se non specificato, è implicitamente package Esempio: public interface MiaInterfaccia { int UNA_COSTANTE_INTERA = 100; String UNA_COSTANTE_STRINGA = "ciao"; void metodo1(int a); char metodo2(String s, long l); } I metodi definiti (dichiarati) in una interfaccia sono implicitamente astratti (non essendone fornita l’implementazione) e pubblici; non sono ammessi metodi dichiarati come static Gli “attributi” di un’interfaccia, invece, sono implicitamente static, final e pubblici
28/12/2001 package18 Interfacce Una interface è una struttura sintattica dotata di nome, che racchiude la specifica della segnatura e del ReturnType dei metodi di una classe non ancora implementata Esempio: interface Driveable { boolean startEngine(); void stopEngine(); float accelerate(float acc); boolean turn(Direction dir); }
28/12/2001 package19 Implementazione di una interfaccia Una interfaccia può essere implementata da una (o più) classi: interface Driveable { boolean startEngine();... } class Automobile implements Driveable { boolean startEngine() {... } // una particolare implementazione …. } class Motorcycle implements Driveable { boolean startEngine() {... } // un’altra implementazione …. } Una classe che implementi una o più interfacce deve implementare tutti i metodi di quelle interfacce
28/12/2001 package20 Interfacce In realtà, un’interfaccia rappresenta un contratto: “chi” si impegna ad implementarla si impegna a mettere a disposizione certe funzionalità Le interfacce non servono solo per “simulare” l’eredità multipla: definiscono un contratto in forma puramente astratta Le interfacce possono ereditare da altre interfacce, anche da più di una contemporaneamente (quindi tra interfacce è ammessa l’eredità multipla)
28/12/2001 package21 Polimorfismo A un metodo che richieda un parametro di un certo tipo classe MiaClasse possiamo passare un oggetto il cui tipo è una sottoclasse di MiaClasse. Ciò rientra nel concetto generale di polimorfismo: data una classe MiaClasse e dichiarata una variabile mc di quel tipo, a mc può essere assegnato un qualunque oggetto che sia istanza di una qualunque sottoclasse (diretta o indiretta) di MiaClasse ; non vale il contrario
28/12/2001 package22 Polimorfismo: esempio class MiaClasse { } class MiaClasseErede extends MiaClasse { } class AltraMiaClasse { MiaClasse mc; public void unMetodo() { MiaClasseErede mce = new MiaClasseErede(); mc = mce; // lecito mce = mc; // errore ! mce = (MiaClasseErede)mc; // lecito }
28/12/2001 package23 Polimorfismo Esempio: Driveable vehicle; /* variabile di tipo interfaccia; le possiamo assegnare qualunque oggetto di una classe che implementa l’interfaccia */ Automobile auto = new Automobile(); Motorcycle moto = new Motorcycle();... vehicle = auto; vehicle.startEngine();/* polimorfismo: è il metodo di Automobile */ … vehicle = moto; vehicle.startEngine();/* polimorfismo: è il metodo di Motorcycle */
28/12/2001 package24 Una classe può implementare più di una interfaccia interface Driveable { interface Rentable { void startEngine(); void startRental(); void stopEngine(); void endRental(); float accelerate(float acc); int book(Date start, Date end); boolean turn(Direction dir);} } class AvisCar implements Driveable, Rentable { void startEngine() { … } void startRental() { … } … } Ereditarietà multipla
28/12/2001 package25 Il modificatore abstract Una classe è dichiarata abstract quando contiene almeno un metodo abstract (cioè senza body) Una classe abstract non può essere instanziata: occorre sovrascrivere tutti i metodi abstract in una sottoclasse, e istanziare la sottoclasse Esempio: abstract class a { … abstract int m(int k); } class b extends a {... int m(int n) { … } } sovrascrive, fornendo la implementazione del metodo
28/12/2001 package26 INTERFACCE vs CLASSI abstract Le interfacce sono simili a classi che abbiano soltanto: metodi abstract campi static e final (cioè costanti) A differenza delle classi, le interfacce permettono di realizzare una forma di ereditarietà multipla
28/12/2001 package27 Ma sono veramente necessarie le interfacce? Non si potrebbero usare le classi astratte al loro posto ? In realtà, le interfacce sono molto diverse dalle classi astratte: le interfacce ci forniscono una forma di eredità multipla le classi astratte possono (se “lo vogliono”) implementare loro metodi e fissare livelli di accesso sui loro membri, mentre le interfacce possono solo dichiarare costanti pubbliche e metodi pubblici (senza mai fornirne l’implementazione) In genere, se non c’è necessità di eredità multipla si preferisce usare le classi astratte... possono implementare dei metodi, i quali, essendo ereditati dalle sottoclassi, non devono essere riscritti In genere, comunque, una classe che si prevede sarà utilizzata (ereditata) da molte altre classi dovrebbe essere l’implementazione di una interfaccia... per il “solito” motivo: una classe può ereditare da una sola classe alla volta...
28/12/2001 package28 Unità di compilazione: riassunto file: MyClass.java package ll.myutil; /* opzionale */ import java.util.* ; /* opzionale */ public class MyClass { … } class MyOtherClass { /* opzionale */ … } interface MyInterface { /* opzionale */ … }