Modificatori: static Variabili e metodi associati ad una Classe anziche’ ad un Oggetto sono definiti “static”. Le variabili statiche servono come singola variabile condivisa tra le varie istanze I metodi possono essere richiamati senza creare una istanza. Variabili “static”: esempio 1 class S { static int instanceCount = 0; //variabile “di classe” S() {instanceCount++;} } public class A { public static void main(String a[]) { new A(); Output: } # of instances: A() { for (int i = 0; i < 10; ++i) { S instance=new S(); } System.out.println("# of instances: "+S.instanceCount); } } 10 Variabili “static”: esempio 2 class S { static int instanceCount = 0; //variabile “di classe” S() {instanceCount++;} public void finalize() {instanceCount--;} } public class A { public static void main(String a[]) { new A();} Output: A() { for (int i = 0; i < 10; ++i) { # of instances: # of instances: S instance=new S(); } System.out.println("# of instances: "+S.instanceCount); System.gc(); System.runFinalization(); System.out.println("# of instances: "+S.instanceCount); } } 10 0 Metodi “static”: esempio 1 class S { static int instanceCount = 0; //variabile “di classe” S() {instanceCount++;} static void azzeraContatore() {instanceCount=0;} } Può agire solo su public class A { public static void main(String a[]) { variabili statiche! new A(); Output: } instanceCount: 2 A() { for (int i = 0; i < 10; ++i) { if (i%4==0) S.azzeraContatore(); S instance=new S(); } System.out.println("instanceCount: "+S.instanceCount); Ruolo: Metodi che agiscono su } variabili statiche } metodi “static”: esempio 2 Notare la maiuscola! (per convenzione) Math.sqrt(double x); System.gc(); System.arrayCopy(...); System.exit(); Integer.parseInt(String s); Float.parseFloat(String s); Ruolo: analogo alle librerie del C Che cos’e’: System.out.println() ? Perchè il main è “static”? public class A { String s="hello"; public static void main(String a[]) { System.out.println(s); } } Non static variable s cannot be referenced from static context public class A { String s="hello"; public static void main(String a[]) { new A; } A() { System.out.println(s); } } hello Sezione: Packages Packages package Una collezione di classi correlate package myclasses; class A {...}; class B {...}; import myclasses.A; import myclasses.*; Annidamento di package package myclasses; class A {...}; package myclasses; class B {...}; package myclasses.veryUsefulClasses; class C {...}; import myclasses.*; // NON importa C! Definizione suggerita di un nome univoco per i packages: È basata sul nome internet (es.: it.unitn.science.mypackage) Annidamento di package I packages si riflettono in una struttura di directories myclasses A.class B.class veryUsefulClasses C.class Sezione: Costruttori Costruttori Definizione dei costruttori Se per una classe A non scrivo nessun costruttore, il sistema automaticamente crea il costruttore A(); Se invece definisco almeno un costruttore non void, ad es. A(int s), il sistema non crea il costruttore A(); Definizione dei costruttori Se B è figlia di A, il costruttore di B come prima cosa invoca A(), a meno che la prima istruzione non sia una super. A() { ... } A(int k) { ... } B(int k) { ... } B(int k) { super(k)... } Invocazione dei costruttori public class A { public A() { System.out.println("Creo A"); } } public class B extends A { public B() { System.out.println("Creo B"); } public B(int k) { System.out.println("Creo B_int”); } } Output: Creo A Creo B_int public static void main(String [] a) { B b=new B(1); } Invocazione dei costruttori public class A { public A(int k) { System.out.println("Creo A"); } } public class B extends A { public B() { System.out.println("Creo B"); } public B(int k) { System.out.println("Creo B_int”); } } Output: ERRORE ! Perchè ? public static void main(String [] a) { B b=new B(1); } Sezione: Modificatori Abstract e Controllo di accesso Modificatori: abstract Classi dichiarate abstract non possono essere istanziate, e devono essere subclassate. Metodi dichiarati abstract devono essere sovrascritti Una class non abstract non può contenere abstract metods Modificatori: visibilità public (non def.) protected private visibile da tutti visibile da tutti nello stesso package visibile dalle sottoclassi Uso di metodi “di accesso”: nascosta da tutti public class ACorrectClass { private String aUsefulString; public String getAUsefulString() { return aUsefulString; // "get" the value } private void setAUsefulString(String s) { //protected void setAUsefulString(String s) { aUsefulString = s; // "set" the value } Matrice degli accessi Access Levels Specifier protected Class Y Y Y Package N Y Y Subclass N N Y World N N N public Y Y Y Y private no specifier Vedi anche http://java.sun.com/docs/books/tutorial/java/javaOO/accesscontrol.html Sezione: Upcast - downcast Upcast & downcast Coercion Una funzione può essere polimorfa senza essere stata disegnata tale intenzionalmente. Sia f una funzione che prende un argomento di tipo T, e S sia un tipo che può essere automaticamente convertito in T. Allora f può essere detta polimorfa respetto a S e T. float somma(float x, float y) accetta anche somma (3, 3.14) somma(2,3) (coercion di int a float) public class Test { public static void main(String a[]) { new Test(); } cast Test() { OK: upcast implicito A a; B b = new B(); NO: "method f2 not a=b; found in class A" a.f1(); (compiler) a.f2(); class A { void f1() } {System.out.println("f1");} } } class B extends A { void f2() {System.out.println("f2");} } class C extends B { void f3() {System.out.println("f3");} } public class Test { public static void main(String a[]) { new Test(); } cast Test() { OK: upcast implicito A a; B b = new B(); a=b; OK: downcast corretto a.f1(); ((B)a).f2(); class A { void f1() } {System.out.println("f1");} } } class B extends A { void f2() {System.out.println("f2");} } class C extends B { void f3() {System.out.println("f3");} } public class Test { public static void main(String a[]) { new Test(); } cast Test() { OK: upcast implicito A a; B b = new B(); a=b; NO: downcast illecito (runtime) a.f1(); java.lang.ClassCastException ((C)a).f3(); class A { void f1() } {System.out.println("f1");} } } class B extends A { void f2() {System.out.println("f2");} } class C extends B { void f3() {System.out.println("f3");} } Type conversion - cast Si può applicare cast SOLO all’interno di una gerarchia di ereditarietà È consigliabile usare l'operatore instanceof per verificare prima effettuare un downcast if (staff[1] instanceof Manager) { Manager n = (Manager)staff[1]; ... } Input/Output, Eccezioni Input da tastiera Try – catch - finally try { System.out.println("Dammi un intero"); i=Integer.parseInt(s.readLine()); System.out.println("Hai scritto "+i); } catch (Exception e) {e.printStackTrace();} finally { doSomethingInEveryCase() } throws Ogni frammento di codice che lancia una eccezione DEVE essere contenuto in un blocco try-catch OPPURE stare nel corpo di un metodo che “throws” una eccezione do() throws SomeException { ... } throw Le eccezioni possono essere generate dall’istruzione throw. throw(new SomeException()); Lettura di stringhe Dammi una stringa abracadabra Hai scritto abracadabra import java.io.*; public class A { public A() { BufferedReader s = new BufferedReader( new InputStreamReader(System.in)); try { System.out.println("Dammi una stringa"); String str=s.readLine(); System.out.println("Hai scritto "+str); }catch (IOException e){ e.printStackTrace(); } } public static void main(String [] ar) { A a=new A(); } } Lettura di int public A() { int i=0; BufferedReader s = new BufferedReader( new InputStreamReader(System.in)); try { System.out.println("Dammi un intero"); i=Integer.parseInt(s.readLine()); System.out.println("Hai scritto "+i); }catch (Exception e) {e.printStackTrace();} } Dammi un intero 2 Hai scritto 2 public A() { int i=0; BufferedReader s = new BufferedReader( new InputStreamReader(System.in)); try { System.out.println("Dammi un intero"); i=Integer.parseInt(s.readLine()); System.out.println("Hai scritto "+i); }catch (IOException e) {e.printStackTrace();} } Lettura di int Dammi un intero pippo java.lang.NumberFormatException: For input string: "gh" at java.lang.NumberFormatException.forInputString(NumberFormatException.ja va:48) at java.lang.Integer.parseInt(Integer.java:426) at java.lang.Integer.valueOf(Integer.java:532) at pila.A.<init>(A.java:11) at pila.A.main(A.java:19) Exception in thread "main" public A() { Dammi un float pippo float f=0; boolean error; Input non valido BufferedReader s = new BufferedReader( Dammi un float new InputStreamReader(System.in)); 3 Hai scritto 3.0 try { do { System.out.println("Dammi un float"); try{ error=false; f=Float.parseFloat(s.readLine()); } catch (NumberFormatException e) { error=true; System.out.println("Input non valido"); } } while (error); System.out.println("Hai scritto "+f); }catch (IOException e) {e.printStackTrace();} } Lettura di float Fondamenti di Java Introduzione alla costruzione di GUI Pluggable Look & Feel Pluggable Look&Feel Scelta del Look&Feel public static void main(String[] args) { try { UIManager.setLookAndFeel( UIManager.getCrossPlatformLookAndFeelClassName()); } catch (Exception e) { } new SwingApplication(); //Create and show the GUI. } UIManager.getCrossPlatformLookAndFeelClassName() Returns the Java look and feel. UIManager.getSystemLookAndFeelClassName() Specifies the look and feel for the current platform. Scelta del Look&Feel public static void main(String[] args) { try { UIManager.setLookAndFeel( "com.sun.java.swing.plaf.gtk.GTKLookAndFeel"); } catch (Exception e) { } new SwingApplication(); //Create and show the GUI. } UIManager.getSystemLookAndFeelClassName(String s) Specifies the look and feel for the platform described by “s”. Available Look&Feel "com.sun.java.swing.plaf.gtk.GTKLookAndFeel" Specifies the GTK+ look and feel. Introduced in release 1.4.2. "javax.swing.plaf.metal.MetalLookAndFeel" Specifies the Java look and feel. "com.sun.java.swing.plaf.windows.WindowsLookAndFeel" Specifies the Windows look and feel. Currently, you can use this look and feel only on Microsoft Windows systems. "com.sun.java.swing.plaf.motif.MotifLookAndFeel" Specifies the CDE/Motif look and feel. This look and feel can be used on any platform.