TARDINI DEVIS
MTR. 35212
1° ESERCITAZIONE DI LABORATORIO
Questa esercitazione è stata tenuta al fine di prendere confidenza con il linguaggio di
programmazione java, che è al centro di questo corso di Linguaggi e Traduttori.
In seguito verrà presentata la realizzazione di un Counter (contatore), realizzato utilizzando più
operazioni messe a disposizione dalla JDK.
Per questi primi due programmi sorgente (Example.java e Counter.java) verrà presentata una
versione che utilizza la peculiarità del package, dove per package si intende un gruppo di classi che
costituiscono una unità concettuale, ed una versione che non la utilizza.
Viene proposto di seguito il sorgente:
Counter.java
package ex1;
/**
*
* A Counter is an object that counts integer values.
* It provides services to be reset,
* to be incremented and to retrieve its value
*
* @author Pippo Baudo
* @version 1.0
*/
public class Counter {
/**
* Resets the counter value.
*
* The value is reset to zero.
*/
public void reset(){
value=0;
}
/**
* Increments the counter value.
*/
public void inc(){
value++;
}
/**
* Gets the counter value.
*/
public int getValue(){
return value;
}
// private data
private int value;
}
Come si può notare all’inizio del file è presente una dichiarazione di package: package ex1.
Questo package di nome ex1, richiede che tutte le sue classi si trovino in una cartella di nome ex1.
Compilando tramite l’apposito comando (javac) questo file, viene creata la classe pubblica Counter
(public class Counter), in essa sono definite le operazioni pubbliche della medesima classe (reset,
inc, getValue).
Queste operazioni pubbliche sono così definite:
reset: resetta il counter portandolo al valore iniziale 0;
inc: incremente il counter di una unità;
getValue: restituisce il valore attuale.
Il campo value è privato, quindi può essere acceduto solo dalle operazioni definite nella medesima
classe (reset, inc, getValue), e nessun altro; in questo modo si garantisce l’incapsulamento.
Di seguito il file sorgente:
Example.java
package ex1;
/**
* Example application explaining
* the use of Counter object
*/
public class Example {
public static void main (String args[]) {
Counter c= new Counter();
c.reset();
c.inc();
c.inc();
System.out.println(c.getValue());
}
}
La frase Counter c definisce un riferimento a counter (una specie di puntatore), l’oggetto counter
viene poi creato dinamicamente tramite il comando new.
L’oggetto referenziato, in questo caso Counter, è quindi direttamente accessibile tramite la
notazione puntata: c.inc(); x = c.getValue();
Si ha quindi che questo programma è fatto di due classi, una che fa da componente software, e ha
come compito quello di definire il main (solo parte statica) e l’altra invece implementa il tipo
counter (parte non statica). A run-time nasce un oggetto: lo crea all’istante il main, quando vuole,
tramite new, a immagine e somiglianza della classe Counter e poi lo usa per nome, con la notazione
puntata, senza bisogno di dereferenziarlo esplicitamente.
Nell’ordine vengono compilate le classi:
javac Counter.java  che produce il file Counter.class
javac Example.java  che produce il file Example.class
la classe counter deve quindi già esistere quando si compila la classe Example.
Per eseguire il programma basta invocare l’interprete con il nome di quella classe (pubblica) che
contiene il main: java Example.
Questa procedura sarebbe stata corretta se non avessimo specificato il package in quanto se una
classe non dichiara di appartenere ad alcun package, automaticamente è assegnata al package di
default, che per convenzione fa riferimento alla cartella corrente.
Per compilare queste due classi mi sono dovuto mettere nella cartella superiore a ex1 ed invocare il
compilatore con il percorso completo della classe:
javac ex1/Counter.java
javac ex1/Example.java
in questo modo ho ottenuto i file.class .
Anche per quanto riguarda l’esecuzione, ho dovuto agire nel medesimo modo: mi sono posto nella
cartella superiore ad ex1 e da lì ho invocato l’interprete con il nome assoluto della classe:
java ex1.Example
Come risultato si ottiene la stampa a video del numero 2.
Infatti se si legge il programma si può notare che inizialmente il contatore viene resettato e
successivamente incrementato per ben due volte; dopodiché viene chiesto che venga restituito il
valore così ottenuto e stampato a video su una linea.
Viene esposto in seguito il medesimo programma senza l’utilizzo del package:
Counter.java
/**
*
* A Counter is an object that counts integer values.
* It provides services to be reset,
* to be incremented and to retrieve its value
*
* @author Pippo Baudo
* @version 1.0
*/
public class Counter {
/**
* Resets the counter value.
*
* The value is reset to zero.
*/
public void reset(){
value=0;
}
/**
* Increments the counter value.
*/
public void inc(){
value++;
}
/**
* Gets the counter value.
*/
public int getValue(){
return value;
}
// private data
private int value;
}
Example.java
/**
* Example application explaining
* the use of Counter object
*/
public class Example {
public static void main (String args[]) {
Counter c= new Counter();
c.reset();
c.inc();
c.inc();
System.out.println(c.getValue());
}
}
Questi due sorgenti rispetto ai precedenti non hanno specificato il package, per questo motivo
cambiano le istruzioni da eseguire per la compilazione ed esecuzione, ma trattandosi di programmi
identici il risultato finale che si ottiene è il medesimo.
Se la classe Counter non fosse stata pubblica, le due classi avrebbero potuto essere scritte nel
medesimo file.java, come viene proposto qui di seguito:
Example.java
package ex2;
public class Example {
public static void main (String args[]) {
Counter c= new Counter();
c.reset();
c.inc();
c.inc();
System.out.println(c.getValue());
}
}
class Counter {
public void reset(){
value=0;
}
public void inc(){
value++;
}
public int getValue(){
return value;
}
// private data
private int value;
}
l’ordine delle classi nel file è irrilevante, non esiste un concetto di dichiarazione che deve precedere
l’uso. Il file prende il nome da quello della classe pubblica, in questo caso Example.java .
Compilando il file otteniamo comunque due file.class, uno per ogni singola classe compilata, ogni
file.class rappresenta quella classe, in quanto un file non può contenere più classi.
Il terzo esempio che qui di seguito verrà proposto serve a spiegare meglio il concetto di uguaglianza
fra oggetti.
Counter.java
package ex3;
/**
*
* A Counter is an object that counts integer values.
* It provides services to be reset,
* to be incremented and to retrieve its value
*
*/
public class Counter {
/**
* Resets the counter value.
*
* The value is reset to zero.
*/
public void reset(){
value=0;
}
/**
* Increments the counter value.
*/
public void inc(){
value++;
}
/**
* Gets the counter value.
*/
public int getValue(){
return value;
}
/**
* Tests if two counters are equal.
*
* Two counters are equal when they have
* the same value.
*/
public boolean equals(Counter x){
return value==x.value;
}
// private data
private int value;
}
Example.java
package ex3;
public class Example {
public static void main (String args[]) {
Counter c1 = new Counter();
c1.reset();
c1.inc();
System.out.println("c1 = "+c1.getValue());
Counter c2 = c1;
c2.inc();
System.out.println("c1 = "+c1.getValue());
System.out.println("c2 = "+c2.getValue());
//
Counter c3 = new Counter();
c3.inc();
System.out.println(c3.equals(c1));
c3.inc();
System.out.println(c3.equals(c1));
}
}
Esaminiamo il file Example.java, inizialmente viene creato il riferimento c1 per l’oggetto Counter,
viene creato l’oggetto Counter, c1 viene prima resettato poi incrementato e successivamente
visualizzato a video, a questo punto c1=1.
Ora viene creato il riferimento c2 per l’oggetto Counter e assegnato a c1 (c2 = c1), in questo modo
l’oggetto Counter referenziato è condiviso, c2 coincide con c1, quindi se si incrementa c2 risultano
incrementati entrambi, tant’è vero che eseguendo il programma a questo punto, viene visualizzato a
video c1 = 2 e c2 = 2.
Viene creato il riferimento c3 per l’oggetto Counter, viene creato l’oggetto Counter, c3 viene
incrementato. Ora verrà eseguita l’operazione pubblica equals, che è stata definita all’interno della
classe Counter. Come si può vedere equals è stata definita in modo che vengano considerati uguali
due Counter se e solo se hanno identico valore ed è proprio per questo che avendo c1 = 2 e c3 = 1,
la richiesta di stampare a video l’equals tra c1 e c3 restituisce false.
Successivamente c3 viene nuovamente incrementato, in questo modo ripetendo l’equals tra c1 e c3
viene restituito true.
Nel esempio che segue vengono utilizzati dei costruttori per inizializzare l’oggetto Counter.
Counter.java
package ex4;
/**
*
* A Counter is an object that counts integer values.
* It provides services to be reset,
* to be incremented and to retrieve its value
*
*/
public class Counter {
/**
* Constructs a counter with default value (1).
*/
public Counter(){
value=1;
}
/**
* Constructs a counter providing a start value.
*/
public Counter(int v){
value=v;
}
/**
* Resets the counter value.
*
* The value is reset to zero.
*/
public void reset(){
value=0;
}
/**
* Increments the counter value.
*/
public void inc(){
value++;
}
/**
* Increments the counter value.
*
* @param n amount of the increment
*/
public void inc(int n){
value+=n;
}
/**
* Gets the counter value.
*/
public int getValue(){
return value;
}
/**
* Tests if two counters are equal.
*
* Two counters are equal when they have
* the same value.
*/
public boolean equals(Counter x){
return value==x.value;
}
// private data
private int value;
}
Example.java
package ex4;
public class Example {
public static void main (String args[]) {
Counter c1 = new Counter();
c1.inc();
Counter c2 = new Counter(10);
c2.inc();
System.out.println("c1 = "+c1.getValue());
System.out.println("c2 = "+c2.getValue());
}
}
Nel file Counter.java sono stati definiti i costruttori, più precisamente con l’istruzione:
public Counter(){
value=1;
}
Viene praticamente definito che alla creazione di un oggetto Counter se non viene passato in
ingresso alcun parametro esso si inizializza automaticamente a 1.
Mentre con l’istruzione:
public Counter(int v){
value=v;
}
si definisce che alla crezione di un oggetto Counter, il valore int passato come parametro è il valore
con il quale viene inizializzato il Counter.
Compilando ed eseguendo i file, come risultato si ottiene la stampa a video del numero 2 e del
numero 11.
Questo guardando il file Example.java è facilmente deducibile.
Viene creato l’oggetto Counter c1 il quale fa scattare il costruttore che lo inizializza a 1,
successivamente viene incrementato.
Viene creato l’oggetto Counter c2 il quale fa scattare il costruttore che lo inizializza a 10,
successivamente viene incrementato.
Viene stampato a video il valore di c1 che è 2 e il valore di c2 che è 11.