Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono...

41
1 Costruire oggetti Costruire oggetti: oggetto di tipo Point • Utilizziamo una delle classi della “libreria” di Java che permette di costruire oggetti di tipo Point, che rappresentano punti del piano con coordinate intere. Per sapere come si costruisce un oggetto di tipo Point dovremo consultare la documentazione delle classi. Nella documentazione vengono descritti i campi, o dati, (forma) e i metodi (funzionalità) che agiscono sull’oggetto. Costruire oggetti: oggetto di tipo Point • Un “punto” viene rappresentato tramite una coppia di numeri interi che rappresentano le sue coordinate x e y. • Se vogliamo creare un oggetto “punto” dobbiamo costruire un’area di memoria in cui inserire i dati dell’oggetto. (par. 2.6) • Per creare un oggetto su usa l’operatore new. Oggetto di tipo Point Esempio. Point p1 = new Point(1, 0); •I dati dell’oggetto p1 sono i due campi: x=1 y=0 I valori 1, 0 si chiamano parametri di costruzione.

Transcript of Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono...

Page 1: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

1

Costruire oggetti

Costruire oggetti: oggetto di tipo

Point• Utilizziamo una delle classi della “libreria” di

Java che permette di costruire oggetti di tipo Point, che rappresentano punti del piano con coordinate intere.

• Per sapere come si costruisce un oggetto di tipo Point dovremo consultare la documentazione

delle classi. Nella documentazione vengono descritti i campi, o dati, (forma) e i metodi (funzionalità) che agiscono sull’oggetto.

Costruire oggetti: oggetto di tipo

Point• Un “punto” viene rappresentato tramite una

coppia di numeri interi che rappresentano le sue coordinate x e y.

• Se vogliamo creare un oggetto “punto”dobbiamo costruire un’area di memoria in cui inserire i dati dell’oggetto. (par. 2.6)

• Per creare un oggetto su usa l’operatore new.

Oggetto di tipo Point

• Esempio.

Point p1 = new Point(1, 0);

• I dati dell’oggetto p1 sono i due campi:

x=1 y=0

I valori 1, 0 si chiamano parametri di costruzione.

Page 2: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

2

Definizione e costruzione di un

oggetto

• Sintassi.

• Definizione

NomeClasse nomeoggetto;

• Costruzione

nomeoggetto =

new NomeClasse(parametri);

Definizione e costruzione di un

oggetto

• Si può anche definire e costruire l’oggetto nella stessa istruzione:

NomeClasse nomeoggetto =

new NomeClasse(parametri);

• NomeClasse è quindi un tipo di dato, diverso dai tipi base.

Operatore new

• Cosa fa l’operatore new:1. crea una nuova area di memoria per

l’oggetto2. inizializza i dati dell’oggetto3. restituisce il riferimento dell’oggetto (la sua

locazione in memoria)

dati o campi

proprietà o metodi

dati o campi

proprietà o metodi

p1

Metodi di accesso e

metodi modificatori

Page 3: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

3

Metodi di accesso e metodi

modificatori

• Le operazioni per le variabili dei tipi base erano accesso e assegnamento.

• Anche per gli oggetti vogliamo poter:• accedere alle informazioni sullo stato dell’oggetto

• modificare lo stato dell’oggetto

• Gli oggetti possono essere usati solo attraverso i metodi della classe:• metodi di accesso e metodi modificatori.

(par. 2.7)

Metodi che agiscono su oggetti

• Un metodo che agisce su oggetti ha le seguenti caratteristiche:

1) ha un nome

2) ha zero, uno o più parametri espliciti

3) restituisce un valore di un certo tipo oppure void

4) ha un parametro implicito: l’oggetto che invoca il metodo.

• Un metodo statico non agisce su oggetti e ha solo le prime tre caratteristiche.

Metodi di accesso e metodi

modificatori

• Metodi di accesso per la classe Point:getX, getY

• Restituiscono come valore (double) i parametri di costruzione dell’oggetto, rispettivamente le coordinate del vertice x e ySystem.out.println(""""ascissa del """"

+ """"punto = """" + p1.getX());

Metodi di accesso e metodi

modificatori• Metodi modificatori per la classe Point.• Vogliamo spostare il punto di 2 unità in

direzione x e in direzione y: ossia eseguire una traslazione. Il metodo translate riceve come parametri le quantità da traslare e cambia lo stato dell’oggetto:

p1.translate(2,2);

//le nuove coordinate del punto

//saranno (3, 2)

Page 4: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

4

Metodi che agiscono su oggetti

• Il metodo getX restituisce un valore di tipo double.

• Un metodo che restituisce un valore di un certo tipo viene invocato in una istruzione che può utilizzare quel valore.

• Il metodo translate è void: non restituisce nulla, ma modifica lo stato dell’oggetto.

• Un metodo di tipo void viene invocato in una istruzione indipendente:nomeoggetto.nomemetodo(parametri);

Metodi di accesso e metodi

modificatori

//costruzione dell'oggetto punto

Point p1 = new Point(1,0);

System.out.println("il punto P ha "

+ " coordinate P(" + p1.getX() +

", " + p1.getY() + ")" );

p1.translate(2,2);

System.out.println("il punto P ora “ +

“ ha coordinate P(" + p1.getX() +

", " + p1.getY() + ")" );

Una classe di collaudo

• La classe Point permette di utilizzare l’oggetto punto p1.

• Per vedere come “funziona” l’oggetto, dobbiamo realizzare una classe di prova che collauda l’oggetto punto: (par. 2.8)• scrivere il main• creare uno o più oggetti nel metodo main• invocare i metodi• visualizzare i risultati prodotti dai metodi

confrontandoli con valori previsti.

Una classe di collaudo

• Come facciamo ad usare la classe Point e i suoi metodi?

• La classe Point appartiene ad un “pacchetto”che contiene strumenti astratti per realizzare finestre e forme grafiche

Abstract Windowing Toolkit awt

• Dobbiamo collegarci a questo pacchetto o, come si dice, “importarlo”.

Page 5: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

5

Pacchetti di classi

I pacchetti di classi (package)

• Le classi della libreria di Java sono raggruppate in pacchetti (package) che contengono classi aventi la stessa finalità.

• Per usare una classe di una libreria, bisogna importarla nel programma. (par.2.8)

• Sintassiimport nomePacchetto.NomeClasse;

• Nel nostro esempio:import java.awt.Point;

I pacchetti di classi (package)

• Le classi System e String appartengono al pacchetto java.lang, che contiene classi di uso fondamentale per la programmazione. Per tale motivo il pacchetto java.lang viene importato automaticamente.

• Si possono importare una o più o tutte le classi di un pacchetto:import java.awt.*;

// * : si importano tutte quelle del

// pacchetto, anche quelle che non

// si usano ...

I pacchetti di classi (package)

• È possibile importare tutte le classi?

import java.*.*; // NO

• È bene importare solo le classi che si utilizzano: si ha una maggiore chiarezza.

• Come possiamo sapere dove sono le classi e quali sono i pacchetti da importare?

Page 6: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

6

La documentazione

della libreria

standard

Documentazione API

• Tutti gli ambienti di sviluppo Java forniscono esaurienti sistemi di supporto: “guide in linea”.

• La documentazione API (ApplicationProgramming Interface) si può trovare all’indirizzo (par. 2.9)

http://java.sun.com/javase/6/docs/api/

index.html

Documentazione API

• La descrizione di una classe comprende l’elenco dei suoi metodi pubblici (la sua interfaccia) ed una sintetica descrizione delle motivazioni alla base del progetto della classe e delle modalità del suo utilizzo.

• Per ogni metodo, vengono indicati• il nome e la funzionalità svolta• il tipo ed il significato dei parametri richiesti, se ci

sono• il tipo ed il significato del valore restituito, se c’è

• le eventuali eccezioni lanciate in caso di errore

Documentazione API

• In un riquadro a sinistra ci sono tutte le classi (All Classes); selezionandone una, nel riquadro a destra apparirà la classe con la sua descrizione.

• Nel riquadro a destra compare un sunto dei vari metodi con indicato il tipo, il nome, …

• Selezionando un metodo si ha un’informazione più dettagliata.

Page 7: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

7

Progettare

Algoritmi

Progettare Algoritmi

• La progettazione di un algoritmo è una fase che richiede intelligenza e fantasia: l’informatica è un’arte.

• Per imparare a progettare un algoritmo ci può aiutare la scomposizione del problema in problemi più semplici e la scrittura dell’algoritmo in un linguaggio intermedio

(pseudocodifica) nel quale evidenziare i costrutti importanti senza vincoli di sintassi.

Page 8: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

8

Progettare Algoritmi

• Scomporre un problema P in sottoproblemi significa individuare problemi più semplici P1, P2, P3 che risolti nell’ordine costituiscono la soluzione.

• Ciascuno dei sottoproblemi può a sua volta essere scomposto nuovamente.

P1 P2 P3

P

Progettare Algoritmi

• Fino a quando si prosegue con queste successive scomposizioni?

• Si prosegue fino al livello di operazioni

elementari (operazioni aritmetiche, confronti, ecc.) o fino ad incontrare problemi già risolti

in precedenza da noi (es. algoritmi di somma, ricerca, ordinamenti,…) o da altri (funzioni matematiche sin(x), gestione di array,…).

Progettare Algoritmi

• Nel linguaggi ad alto livello (Pascal, C, Java,..) ci sono degli enunciati (comandi) che organizzano le istruzioni con precisi significati: strutture di controllo.

• Sono essenzialmente tre: sequenza, scelta

(decisioni), ciclo (iterazioni).

• Teorema di Bohm-Jacopini 1966: ogni algoritmo può essere scritto utilizzando unicamente queste tre strutture.

Strutture di controllo

Page 9: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

9

Strutture di controllo

• Una struttura di controllo è un blocco di istruzioni caratterizzato da un unico punto di ingresso e un unico punto di uscita e che si può schematizzare nel modo seguente:

SS

Strutture di controllo• In tale modo l’algoritmo si può schematizzare:

S1

Si

Si+1

Sn

prima 2)

successiva 3)

ultima 4)

……

……

Sequenza

• Si chiama sequenza una funzione che ha per dominio un sottoinsieme finito dei ℕ e il cui codominio acquisisce l’ordine posizionaledegli elementi di ℕ .

• Indichiamo con Nk = {1, 2, 3, .., k} s : Nk → A

• Il codominio di s{s(1), s(2), … s(k)} ma solitamente si scrive:

s1 ,s2, s3, …. sk

• si+1 è il successivo di si, come posizione e non come valore

Sequenza

• La struttura di controllo sequenza rappresenta un gruppo di istruzioni eseguite secondo

l’ordine posizionale (che nei linguaggi èl’ordine di scrittura delle istruzioni):

<istruzione 1>

<istruzione 2>

.……………

<istruzione k>

• Cosa può essere <istruzione i> ?

Page 10: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

10

Sequenza

• La generica istruzione può essere:

• assegnazione

• struttura di controllo

• operazione lettura/scrittura

• invocazione di un metodo

Esercizio

• Problema: Si consideri un trapezio T i cui angoli alla base maggiore sono rispettivamente 30° e 45°. Sono note le misure dei lati AB = 60 cm.(base maggiore) e AD = 20 cm. (il lato obliquo che forma 30° con la base). Calcolare il perimetro e l’area del trapezio.

D C

A K H B

Esercizio

• Analisi del problema.

• Vediamo di generalizzare alcuni dati: possiamo voler risolvere il problema per dei valori generici di AB e AD (purché AB >AD).

• Non possiamo invece considerare un valore qualunque per gli angoli alla base, perchéforniscono importanti relazioni per individuare le misure degli altri lati.

Esercizio

• Il problema propone già una scomposizione:

• I scomposizione:

• P si suddivide in• P1 : calcolare il perimetro

p = AB+AD+DC+CB • P2: calcolare l’area

a = (AB+DC)*CH /2

• Base di conoscenza: le formule sono note.

Page 11: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

11

Esercizio

• Scomposizioni successive:• P1 : calcolare il perimetro

• P1.1 calcolare DC• P1.1.1 AK = AD * √ 3 /2• P1.1.2 HB = CH = DK = AD/2• P1.1.3 DC = AB-AK-HB

• P1.2 calcolare CB = HB * √2 • P1.3 p = AB+AD+DC+CB

• P2: calcolare l’area• P2.1 CH = HB • P2.2 a = (AB+DC)*HB/2

Esercizio per casa

• Esercizio. Scrivere in Java le istruzioni di questo algoritmo (sono tutte assegnazioni, ma bisogna rispettare l’ordine).• Scegliere un nome per la classe, definire le variabili con il

tipo double, assegnare i valori per i lati, utilizzare Math.sqrt(2) per il calcolo della radice quadrata (i dati relativi agli angoli sono serviti solo per trovare le relazioni).

• Esercizio. Calcolare la misura della diagonale del rombo equivalente agli 8/5 di un trapezio essendo nota la misura dell’altra diagonale.

Predicati

Predicati

• Un predicato è una funzione a valore nell’insieme B B B B

P: A → B B B B x ∈ A P(x) può essere vero o falso

• x deve avere un valore, altrimenti il predicato non è valido.

Esempio. A = ℝℝℝℝ P(x) : x>5P(7) è vero P(3) è falso

Page 12: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

12

Struttura

condizionale

Struttura condizionale

• Sia P un predicato (condizione); P viene valutato e sarà o vero o falso. Si vuole eseguire <istruzione1> nel caso in cui P sia vero e <istruzione2> nel caso in cui P sia falso, oppure può anche accadere che non dobbiamo fare nulla nel caso in cui P sia falso:

se P

allora istruzione1 //P vero

altrimenti istruzione2 //P falso

//fine scelta

se P

allora istruzione1 //P vero

//fine scelta

Struttura condizionale

• Esempio.• Dati due numeri reali a e b, determinare il più

grande dei due.• Analisi.• Tra le operazioni elementari sui numeri non

c’è il calcolo del massimo, quindi dobbiamo utilizzare una struttura condizionale: il predicato sarà rappresentato dal confronto tra i due numeri; il confronto è una operazione elementare.

Struttura condizionale

• Progetto.Algoritmo massimotradue

variabili a, b, max di tipo reale

acquisire i dati per a e b e stamparli

se a>b

allora max ←←←← a

altrimenti max ←←←← b

//fine scelta

stampare il valore di max

//fine algoritmo

Page 13: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

13

Struttura condizionale

• L’enunciato if . (par. 5.1) • Sia P un predicato (condizione), la sintassi è:

if(P)

istruzione; //una sola istruzione

if(P){//blocco di istruzioni

………

istruzione;

………

}

se P

allora istruzione

//fine scelta

Struttura condizionale

• L’unica istruzione, o il blocco di istruzioniindividuato dalla coppia di parentesi graffe, viene eseguita solo nel caso in cui il predicato P risulti vero.

• Esempio.int a, b;

//assegnare i valori ad a e b

// e stamparli

if(a>b)

System.out.println(""""a e' maggiore """"

+ """" di b"""");

Struttura condizionale

• Sintassi con le due alternative; sia P la condizione:if (P)

istruzione;

else

istruzione;

if(p){//blocco

istruzione;

}

else{//blocco

istruzione;

}

se P

allora istruzione

altrimenti istruzione

//fine scelta

Struttura condizionale• Attenzione al ;• Dopo la parentesi graffa (prima di else) non ci

deve essere il simbolo ;• Se si mette il ; l’istruzione if termina e il

compilatore segnala che c’è una else senza ifif(x>0){

System.out.print(""""x = """" + x);

System.out.println(""""e' positivo"""");

};

else ...

il compilatore segnala:'else' without 'if'

Page 14: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

14

Struttura condizionale

• Traduciamo l’algoritmo massimotradue

public class Massimo2{

public static void main(String[] arg){

double a,b, max;

a=10; b=27; //assegnazione

if (a>b)

max = a; //P vero

else

Struttura condizionale

• Se vogliamo eseguire due istruzioni, dobbiamo usare un blocco:

if (a>b) {//P vero max = a; System.out.println(""""a > b"""");

}else {// P falso

max = b;

System.out.println(""""b >= a"""");}System.out.println(" " " " max = """" + max);

Struttura condizionale

• L’istruzione System.out.println("""" max = """" + max);

• viene eseguita con qualunque valore di P (vero, falso) e rappresenta il punto di prosecuzione dell’esecuzione dell’algoritmo.

• Ma se abbiamo più scelte come possiamo scriverle? In sequenza o annidate? (par. 5.3)

Struttura condizionale

• Scelte multiple. Siano P e Q due predicati, possiamo avere:1) if in sequenza

if (P)

istruzione;

if(Q)

istruzione;

2) if annidate

if(P) (oppure) if(P)

istruzione; if(Q)

else if(Q) istruzione;

istruzione;

Page 15: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

15

Struttura condizionale

• Nel primo caso il predicato Q viene valutato in ogni caso: P vero e P falso.

• Nel secondo caso, il predicato Q viene valutato solo se P è falso; oppure solo quando P è vero.

• Quale delle due strutture scegliere dipende da ciò che si vuole realizzare nell’algoritmo. L’ordine con cui si effettuano le scelte può essere fondamentale per l’algoritmo: un ordine diverso può dare un algoritmo errato.

Struttura condizionale

• Esempio. Supponiamo di voler stampare una stringa che esprima la ricchezza o meno di una persona in base al suo saldo bancario

povero medio ricco straricco

0 1000 50000 200000

• Dopo aver acquisito il valore del saldo (double) eseguiremo i vari confronti con i valori che individuano gli intervalli di minore o maggiore ricchezza stabilendo un valore da stampare (String).

Struttura condizionale

String s; double saldo = ...;

if(saldo >= 200000)

s="straricco";

else if(saldo >= 50000)

s="ricco";

else if(saldo >= 1000)

s="medio";

else if(saldo >=0)

s="povero";

else s="valore non valido";

System.out.println(s);

Struttura condizionale

• Casi di prova.• Per essere sicuri che la struttura funzioni bene

dobbiamo provare tutte le alternative, provando diversi valori per saldo:-2 900 1000 1200 51000 200000 250000

• In corrispondenza a questi valori ci aspettiamo un valore per s: non valido, povero, medio, medio, ricco, straricco, straricco.• Se nel predicato si mette > invece di >= il secondo e il quarto valore di s cambiano.

Page 16: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

16

Struttura condizionale• Proviamo ad invertire l’ordine delle scelte:

if(saldo >= 1000)

s="medio";else if(saldo >= 0)

s="povero";else if(saldo >= 50000)

s="ricco";else if(saldo >=200000)

s="straricco";else s="valore non valido";

• Per saldo = 1200 si ha s= “medio” e le altre scelte nonvengono eseguite; cosa accade per saldo = 51000?

Struttura condizionale• Se mettiamo le if in sequenza otteniamo:if(saldo >= 200000)

s="straricco";if(saldo >= 50000)

s="ricco";if(saldo >= 1000)

s="medio";if(saldo >=0)

s="povero";//else s="valore non valido";System.out.println(s);

• Se il saldo fosse 200000, verrebbe stampato l’ultimovalore perché le assegnazioni sono in sequenza .

Struttura condizionale

• Esercizio. Scrivere delle istruzioni che autorizzano il prelievo da un conto corrente solo se l’ammontare del prelievo è inferiore al saldo:

double saldo = 10000; //saldo iniziale

double prelievo = 200;

if (prelievo <= saldo )

saldo = saldo - prelievo;

System.out.println(""""restano """" + saldo +

"""" euro"""");

Struttura condizionale

• E se il prelievo è superiore? Il programma deve dare una risposta anche nel caso in cui il prelievo sia superiore al saldo e …. impedirlo: il saldo non può essere negativo.

if (prelievo <= saldo )

saldo = saldo - prelievo;

if (prelievo > saldo)

System.out.println("impossibile: conto scoperto");

• In questo algoritmo c’è un errore logico.

Page 17: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

17

Struttura condizionale

• Se il prelievo viene eseguito ma supera la metàdel saldo, la seconda if viene eseguita e verràstampato “impossibile”, perché il saldo è stato modificato.

• Eseguiamo, invece, le istruzioni in alternativa:if (prelievo <= saldo )

saldo = saldo - prelievo;

else

System.out.println("impossibile:"

+ " conto scoperto");

Struttura condizionale

• If annidate e il problema dell’else sospeso.• Siano P e Q due predicati; non essendoci un

costrutto “endif” si pone il seguente problema:if(P)

if(Q)

istruzione1;

else istruzione2;

• La else a quale delle due if si riferisce?(Errori comuni 5.2)

Struttura condizionale

• Esempio.int a,b,c;

a=9; b=7; c=4;

if (a>b) //vero

if(b<c) //falso

b=b+1;

else b=b-1;

System.out.println("""" b = """" + b);

• Quale valore viene stampato per b? 6 o 7? • La else si riferisce alla prima if o alla seconda?

Struttura condizionale

• La regola del linguaggio è la seguente:• La else si riferisce alla if più vicina (interna)

quindi b=6.• Si può alterare la regola inserendo della

parentesi graffe:int a,b,c; a=9; b=7; c=4;

if (a>b){

if(b<c)

b=b+1;}

else b=b-1;//si riferisce alla prima if

System.out.println("""" b = """" + b); //7

Page 18: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

18

Un po’ di stile

• Quando scriviamo una struttura è bene utilizzare una modalità di scrittura che faciliti la lettura dell’algoritmo, rientrando di alcuni spazi a sinistra le istruzioni che si riferiscono al vero e al falso, ed incolonnando le elsesotto la parola if.

• Però questo stile non risolve l’attribuzione della else in caso di più strutture condizionali, che si ottiene con l’inserimento (o meno) della coppia di parentesi graffe.

Operatori di

confronto

Operatori di confronto

• Abbiamo visto con i tipi numerici degli operatori di relazione con i quali si potevano effettuare confronti: (par. 5.2.1)

< > <= >= == !=

• Nel caso di operatori composti con due

simboli non si devono introdurre spazi.

• Errore frequente: confondere= (assegnazione) a = 3;

== (confronto di uguaglianza) if (a == 3)

Operatori logici

Page 19: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

19

Operatori logici

• I predicati si possono comporre con degli operatori (connettivi) logici (booleani):

(par. 5.4.3)

&& (and) || (or) ! (not)

• Sia P un predicato, e sia D il sottoinsieme di A per il quale P(x) è vero:

P : A → B B B B D = { x | P(x)}

Operatori logici

• Congiunzione: and && e

• Siano P e Q due predicati e siano A e B gli insiemi associati al vero.

• P e Q è vero ⇔⇔⇔⇔ sono entrambi veri

P Q P e Q

V V V

V F FF V F A ∩∩∩∩ B intersezione

F F F

Operatori logici

• Disgiunzione: or || o

• Siano P e Q due predicati e siano A e B gli insiemi associati al vero.

• P o Q è falso ⇔⇔⇔⇔ sono entrambi falsiP Q P o QV V VV F VF V V A ∪∪∪∪ B unione

F F F

Operatori logici

• Negazione: not ! non

• Sia P un predicato e sia A l’insieme associato al vero.

• P vero ⇒⇒⇒⇒ non P falso e viceversa

P non P

V F

F V A complementare

Page 20: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

20

Operatori logici

• Nella logica classica si considerano anche altri operatori:

• nand (not and) complementare dell’intersezione

P Q P nand QV V FV F VF V V A ∩∩∩∩ B

F F V

Operatori logici

• nor (not or) complementare dell’unione

P Q P nor Q

V V F

V F FF V F A ∪∪∪∪ B

F F V

Operatori logici

• xor (or esclusivo) differenza simmetrica

P Q P xor Q

V V F

V F VF V V (A ∪∪∪∪ B) - (A ∩∩∩∩ B)

F F F

Operatori logici

• Leggi di De Morgan (Argomenti av. 5.5)

A ∪∪∪∪ B = A ∩∩∩∩ B

A ∩∩∩∩ B = A ∪∪∪∪ B

• L’algebra booleana, che considera solo i valori vero e falso, ha trovato applicazione nella progettazione dei circuiti elettronici: F(a1, a2, … an) funzione con n≥ 1 ingressi rappresenta una porta logica: dispositivo che produce l’uscita 0 o 1 a seconda della funzione logica che rappresenta. Ad esempio una “porta and” avràin uscita 1 se e solo se tutti gli ingressi sono 1.

Page 21: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

21

Operatori logici

• In tale modo si costruiscono gli “addizionatori di bit”per realizzare circuiti (più porte logiche collegate tra loro) per eseguire la somma; ad esempio consideriamo due possibili ingressi

0 + 0 = 00 + 1 = 11 + 0 = 11 + 1 = 0 e riporto 1

primo secondo bit in uscita ingresso ingresso

S. Congiu: Calcolatori elettronici

Porte logiche: not or and

S. Congiu: Calcolatori elettronici

Porte logiche: nand Uso di and e or

• Problema. Dati tre numeri reali a, b, c stabilire se sono i lati di un triangolo e di quale triangolo si tratta.

• Analisi.1. Per essere delle misure di segmenti devono essere

tutti e tre positivi.2. Per essere i lati di un triangolo, ciascuno deve essere

minore della somma degli altri due3. Per essere un triangolo equilatero tutti e tre i lati

devono essere uguali4. Per essere isoscele due lati sono uguali (si hanno tre

possibili coppie)5. Se il triangolo non è né equilatero né isoscele allora

è scaleno.

Page 22: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

22

Uso di and e or

1. Per essere delle misure di segmenti devono essere tutti e tre positivi, pertanto and:

a>0 e b>0 e c>0(a> 0) && (b>0) && (c>0)

2. Per essere lati di un triangolo, ciascuno deve essere minore della somma degli altri due, pertanto and:

a<b+c e b<a+c e c<a+b(a<b+c) && (b<a+c) && (c<a+b)

Uso di and e or

3. Per essere equilatero tutti e tre i lati devono essere uguali:

a = b e b = c (a == b) && (b == c)

• Attenzione: non si scrive a==b==c

• Analogamente: la scrittura matematica 0 ≤ x ≤ 1

• si scrive componendo con and due predicati:(0 <= x) && (x <= 1)

Uso di and e or

4. Per essere isoscele due lati devono essere uguali e si hanno tre possibili coppie, pertanto or:

a=b o b=c o a=c

(a == b) || (b == c) || (a == c)

5. La condizione è in alternativa alle condizioni 3. e 4. .

Operatori con i bit

• In Java esistono operatori binari che agiscono sui singoli bit: & (and), | (or), ^ (or esclusivo) e un operatore unario – (negazione).

• Queste operazioni si possono applicare a variabili booleane o intere. Quando agiscono su variabili intere, l’operazione è applicata ai singoli bit. (Appendice I)

• Il significato è quello dell’operazione rappresentata:

0&0 è 0 (falso); 0 | 1 è 1(vero); …

Page 23: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

23

Operatori con i bit

• Vediamo come opera su variabili intere. Esempio. (Appendice I)

46 & 13 il risultato in decimale sarà 12

Dobbiamo infatti pensare alla rappresentazione binaria dei due numeri e poi agire con & sui singoli bit: consideriamo 32 bit (tipo int)

46 = 00….0101110; 13 = 00…. 0001101

• L’operatore inizia ad agire dal bit più a destra.

Operatori con i bit

• Pensiamo ai bit incolonnati:

0 0 …. 0 1 0 1 1 1 0

0 0 …. 0 0 0 1 1 0 1 &

0 0 …. 0 0 0 1 1 0 0

• Il numero binario 000…. 001100 corrisponde al numero decimale 2 3 + 2 2 = 12.

• Con or 46 | 13 abbiamo il numero binario

00…. 0101111 che corrisponde a

2 5 + 2 3 + 2 2 + 2 1 + 2 0 = 32 + 8+4+2+1 = 47

Operatori con i bit

• Esistono anche altri operatori, detti di scorrimento: <<, >>, >>>.

• Questi operatori spostano i bit verso sinistra (<<) e verso destra (>> lascia il segno, >>> sposta anche il bit del segno).

• Lo spazio “lasciato vuoto” viene riempito con 0.

• In questo corso non useremo questi operatori sugli interi e come operatori logici useremo solo &&, ||, !.

Associatività e

precedenza degli

operatori

Page 24: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

24

Associatività degli operatori

• In espressioni senza le parentesi è necessario stabilire l’ordine con cui vengono valutate le espressioni.

• Gli operatori seguono delle regole di precedenza e associatività. (Appendice E)

• Indichiamo con op un generico operatore binario che coinvolge le variabili x, y, z e consideriamo questa espressione

x op y op z

Associatività degli operatori

• Si dice che un operatore associa a sinistra se l’espressione

x op y op z

viene valutata nel modo seguente: (x op y) op z

• Invece si dice che un operatore associa a destra se viene valutata

x op (y op z)

Associatività degli operatori

• Ad esempio, gli operatori aritmetici associano a sinistra:

x + y + z

viene valutata nel modo seguente: (x + y) + z

analogamente per *, \, %, -• Anche gli operatori logici seguono delle regole

di precedenza e associatività in espressioni senza le parentesi.

Precedenza degli operatori

• Per gli operatori logici la valutazione viene fatta da sinistra a destra, associano a sinistra:

x && y && z (x && y) && z

• Si possono costruire espressioni e predicati componendo operatori logici, aritmetici e di confronto.

Page 25: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

25

Precedenza degli operatori

• L’operatore not precede gli operatori aritmetici, seguono poi gli operatori di confronto, l’operatore and ed infine all’operatore or.

• Attenzione. Altri linguaggi utilizzano precedenze diverse; nei casi dubbi è sempre consigliabile utilizzare le parentesi.

Precedenza degli operatori

• Valutazione pigra dei predicati. (Argomenti av. 5.4)

• In una espressione booleana composta da due o più predicati che utilizzano gli operatori && e ||, la valutazione si ferma non appena si può decidere il valore di verità dell’espressione.

• Nel predicato P && Q, se P è falso Q non viene valutato.

• Nel predicato P || Q, se P è vero Q non viene valutato.

Precedenza degli operatori

• Esempio.if((x>5 && x<10) || (y<7))

nel caso x=8, il predicato y<7 non verràvalutato, essendo vero il primo.

• E bene però non approfittare di tale regola considerando un possibile secondo predicato privo di significato: il predicato composto non è più simmetrico.

• Se si vuole eseguire il confronto completo, si possono usare gli operatori & e |.

Precedenza degli operatori

• Introducendo le parentesi rotonde possiamo modificare la precedenza nella valutazione:if (!(x < 0 || x > 10))

// vero se 0≤≤≤≤ x ≤≤≤≤10 : x>=0 and x<=10 :

// non(x<0 or x>10) leggi di De Morgan

if (!(x < 0) || x > 10)

// vero se x ≥≥≥≥ 0 oppure se x>10

//e quindi vero se x ≥≥≥≥ 0 : non(x<0)

Page 26: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

26

Errori con gli operatori

• Espressioni matematiche del tipo:

0 ≤≤≤≤ x ≤≤≤≤ 10 0<=x<=10 //NO

x e y ≤≤≤≤ 0 x && y <=0 //NO

devono essere scritte componendo due

predicati:1. x>=0 && x<=10

2. x<=0 && y<=0

• Perché il compilatore segnala errore?

Errori con gli operatori

• Caso 1. Il compilatore analizza l’espressione logica e trova due operatori di confronto, quindi esamina il primo confronto (x<=0) da sinistra stabilendo che il risultato sarà un valore booleano; successivamente esamina il secondo operatore relazionale (<=10): dei due operandi, il primo è di tipo boolean, mentre il secondo è di tipo int e segnala un errore:operator <= cannot be applied toboolean,int

Errori con gli operatori

• Caso 2. Il compilatore analizza l’espressione logica e trova un operatore di confronto <= che ha la precedenza sull’operatore booleano &&, il risultato del confronto sarà un valore di tipo boolean e si troverà ad applicare l’operatore && ad un operando di tipo numerico (x) ed uno di tipo boolean, segnalando:operator && cannot be applied to

int,boolean

Leggere dati in

ingresso

Page 27: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

27

Leggere dati in ingresso

• Nei programmi visti finora abbiamo dato un valore iniziale ai dati eseguendo delle assegnazioni: in tale modo avremo sempre la stessa elaborazione ad ogni esecuzione:• massimo tra due numeri, acronimo, trapezio, …

• Se vogliamo eseguire il programma su altri dati, è necessario modificare il codice sorgente (in particolare, le inizializzazioni delle variabili) e compilarlo di nuovo, prima di eseguirlo.

Leggere dati in ingresso

• Per poter scrivere programmi generali, dobbiamo permettere all’utente di inserire dei propri dati: i programmi devono perciò ricevere dati in ingresso.

• Lo scambio di informazioni tra l’utente e il programma e viceversa è rappresentato da un flusso di dati.

• Quando l’ingresso è rappresentato dalla tastiera si dice che il programma viene eseguito in maniera interattiva: durante l’esecuzione il programma si ferma in “attesa”di ricevere i dati (input).

Leggere dati in ingresso

• Il flusso di dati per l’uscita è un oggetto di nome System.out. Per System.out, di tipo PrintStream, è disponibile un metodo printche trasmette le informazioni (stringhe, numeri, caratteri, …).

• Il flusso di dati per l’ingresso è un oggetto di nome System.in. Per l’oggetto System.in, di tipo InputStream, le cose sono più complicate perché questa classe non possiede metodi comodi per la ricezione di dati numerici e stringhe.

Leggere dati in ingresso

• La classe InputStream ha un metodo in grado di leggere un byte alla volta (oppure sequenzedi byte) ma non altri dati.

• Quando introduciamo i dati, introduciamo delle sequenze di caratteri che rappresentano il valore di un tipo di dato: ciò che viene inserito da tastiera viene codificato in binario e successivamente ricostruito prima come gruppo di caratteri (stringa) e poi interpretato come valore di una variabile del tipo di dato.

Page 28: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

28

Leggere dati in ingresso

• Esempio.3 3 intero7.5 7.5 realeciao 0100110…01 ciao stringatrue true booleano

• Occorrono dei metodi per poter interpretare i diversi tipi di dato in ingresso.

• Vedremo due classi per gestire la lettura: la classe Scanner e la classe Bufferedreader, ciascuna con i suoi metodi.

Leggere dati in ingresso

• La classe Scanner rende abbastanza agevole la lettura dei dati. (par. 4.7)

• Il flusso di dati di ingresso System.in viene utilizzato per costruire un oggetto di tipo Scanner (“scansionatore”), sul quale possono agire dei metodi per leggere l’intero “successivo”, il reale “successivo”, la stringa “successiva”, il booleano “successivo”.

Leggere dati in ingresso

• Con l’istruzioneScanner in = new

Scanner(System.in);

si costruisce un oggetto in con il quale si possono invocare i metodi nextDouble, nextInt, nextBoolean, next per acquisire rispettivamente il prossimo valore di: un numero in virgola mobile, un numero intero, un logico e una stringa.

Leggere dati in ingresso

• I valori sono separati da spazi o da tabulazioni, se stanno sulla stessa riga, oppure da un fine riga (premere il tasto Invio).

• È possibile anche leggere l’intera riga, come stringa, utilizzando il metodo nextLine.

• I metodi precedenti, applicati all’oggetto in, restituiscono rispettivamente un valore di tipo double, int, boolean e String.

Page 29: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

29

Leggere dati in ingresso

• La classe Scanner fa parte del pacchetto java.util che deve essere importato:

import java.util.Scanner;

• Vedremo più avanti come acquisire le informazioni da un file di dati, invece che da tastiera: il file con le informazioni dovrà essere costruito, prima di mandare in esecuzione il programma.

Leggere dati in ingresso

• Nella modalità di inserimento da tastiera, quando si incontra una operazione di “lettura”il programma “resta in attesa” dei valori da acquisire.

• Per ricordare “all’utente” i valori di quali variabili devono essere introdotti, può essere utile inserire delle “stampe” che ricordino il nome di tali variabili.

• Si deve sempre ricordare che l’acquisizione èsequenziale.

Leggere dati in ingresso

• Esempio.System.out.println(""""inserire un"""" +

" " " " numero reale, un intero, """" +

"""" un booleano e una stringa"""");

double a = in.nextDouble();

int b = in.nextInt();

boolean c = in.nextBoolean();

String d = in.next();

//inserire valori per a,b,c,d

Leggere dati in ingresso

• I progettisti della classe Scanner hanno usato la localizzazione.

• Significa che il comportamento del programma è legato alla configurazione del sistema su cui viene fatto eseguire.

• A seconda della configurazione (anglosassone o italiana) un valore di tipo double dovràessere inserito nella forma:

parteIntera.parteDecimale � ad esempio 4.35parteIntera,parteDecimale � ad esempio 4,35

Page 30: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

30

Leggere dati in ingresso

• Per uniformità con quello che avviene in altri linguaggi (si possono voler usare gli stessi dati in programmi scritti in linguaggi diversi), conviene inserire i dati reali con il punto decimale. Per questo si deve esplicitamente richiedere la localizzazione anglosassone:

import java.util.Locale;

e prima di eseguire la lettura inserire:in.useLocale(Locale.US);

Leggere dati in ingresso

• È importante non confondere i metodi next e nextLine: entrambi restituiscono una stringa, ma il primo restituisce come stringa il gruppo di caratteri che termina con uno spazio, o fine riga o tabulazione, mentre il secondo restituisce l’intera riga, che può essere composta da un gruppo di parole anche separate da spazi.

• Questo può essere utile se si vogliono inserire parole composte (ad esempio, un cognome composto da due parole).

Leggere dati in ingresso

• Esempio.

String citta = in.nextLine();

// La Spezia

String stato = in.next();

// Italia

Assegnazione tra

riferimenti

Page 31: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

31

Assegnazioni tra riferimenti

• Con l’istruzionePoint p1 = new Point(1,0);

• abbiamo costruito un oggetto punto a cui sono associate due aree di memoria: l’oggetto e la variabile p1.

• p1 è una variabile il cui tipo è la classe Point e contiene il riferimento all’area di memoria che rappresenta l’oggetto creato.

Assegnazioni tra riferimenti

• Le aree di memoria di p1 e dell’oggetto sono diverse e le abbiamo indicate con bordi diversi: queste aree che si trovano in zone diverse della memoria:

oggettovariabile di un

tipo base

p1

Assegnazioni tra riferimenti

• I tipi base e i riferimenti a oggetti stanno in una zona della memoria chiamata Stack: la loro locazione di memoria è assegnata in fase di compilazione.

• Gli oggetti stanno in una zona della memoria chiamata Heap: l’area di memoria viene creata

durante l’esecuzione del programma tramite l’operatore new che ne restituisce il riferimento (che dovrà essere assegnato ad una variabile oggetto del tipo della classe).

Assegnazioni tra riferimenti

• Il riferimento è vincolato al suo tipo.• In una variabile di tipo NomeClasse si possono

memorizzare riferimenti solo del tipo NomeClasse:

Point p1 = new Point(1,0);//esatto

String punto =

new Point(5,10);//ERRATO

Page 32: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

32

Assegnazioni tra riferimenti

• Nei tipi base potevamo fare:int a, b;

a=5;

b=a;

• Avevamo quindi due variabili intere contenenti lo stesso valore.

• È possibile eseguire assegnazioni anche con i riferimenti?

Assegnazioni tra riferimenti

• Consideriamo l’istruzione

Point p2;

• p2 è una variabile di tipo Point e quindi può contenere riferimenti ad oggetti di quel tipo e possiamo fare:

p2 = p1;

p2

Assegnazioni tra riferimenti

• Ha lo stesso significato di: b=a ? Non proprio ….

• Le variabili p1 e p2 sono due variabili distinte, ma l’oggetto è uno solo.

p1 p2

Assegnazioni tra riferimenti

• La variabile p2, con l’assegnazione, riceve il riferimento di p1 e quindi “vede” la stessa area di memoria:

• Non viene creato un nuovo oggetto, perchénon è stato fatto new.

x=1 y=0x=1 y=0p1

p2

Page 33: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

33

Assegnazioni tra riferimenti

• Attraverso p2 possiamo cambiare lo stato dell’oggetto:

p2.translate(3,1);

System.out.println(p1.getX());

System.out.println(p1.getY());

// nuove coordinate x=6, y=3

• I due riferimenti possono entrambi agiresull’oggetto e modificarlo.

Assegnazioni tra variabili di tipo

base

• Per le variabili dei tipi base, invece, si hanno due diverse aree di memoria, ciascuna con un suo valore:

int a=10;

int b;

10

b

a

Assegnazioni tra riferimenti

• Consideriamo le seguenti assegnazioni:

b=a;

a=7;

• Le variabili a e b sono diverse: a=7 e b=10.• Anche p1 e p2 sono due variabili diverse, ma

l’oggetto che “vedono” è unico.

10

b

7

a

Conversioni e

approssimazioni

Page 34: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

34

Conversioni e approssimazioni

• In Java si può assegnare ad una variabile double un valore intero, mentre non èpossibile il viceversa, e neppure assegnare un valore long ad una variabile di tipo int(anche se il valore è valido per int):int a = 10; double b = 15;

float c; long x = 40;

a = b; //ERRORE

c = b; //ERRORE

a = x; //ERRORE

Conversioni e approssimazioni

• Ma se fosse necessario?• Per convertire un tipo “superiore” ad uno

“inferiore” si esegue una esplicita istruzioneche garantisce al compilatore che la eventuale perdita di precisione è voluta: si effettua cioèuna conversione forzata (cast).

• Sintassi.(nometipo) espressione

(par. 4.1)

Conversioni e approssimazioni

• Esempio.a = (int) b;

c = (float) b;

a = (int) x;

• Nel caso di a e b, se b avesse dei decimali il valore di b sarebbe troncato:

b = 5.8;

a = (int) b; //a vale 5

Conversioni e approssimazioni

• Se invece vogliamo un arrotondamento (adeve valere 6) usiamo il metodo rounddella classe Math

x = Math.round(b); //x è long

• Il metodo round restituisce un valore di tipolong e quindi è necessario un cast per assegnarlo ad a:

a = (int) Math.round(b);

Page 35: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

35

Conversioni e approssimazioni

• Il metodo round è un metodo statico e per invocarlo si utilizza il nome della classe:

Math.round(argomento)

• Altri metodi della classe:sqrt, sin, cos, abs, exp, log,…

(par. 4.4 Tabella 2)

• La classe Math appartiene a java.lang e quindi è automaticamente caricata.

Conversioni e approssimazioni

• Se i numeri di tipo long o double non rappresentano bene i calcoli che si vogliono eseguire, si possono utilizzare le classi BigInteger e BigDecimal ed eseguire le operazioni con gli oggetti di quelle classi:

(Argomenti av. 4.1)

Esempio.double d1 = 4.35*100;

System.out.println("d1 = " + d1);// d1 = 434.99999999999994

Conversioni e approssimazioni

• I numeri reali del calcolatore sono approssimati; alcuni numeri con rappresentazione decimale finita hanno rappresentazione binaria periodica.

BigDecimal x = new BigDecimal("4.35");

BigDecimal y = new BigDecimal("100");

BigDecimal z = x.multiply(y);/* si deve usare un metodo per fare il prodotto */System.out.println("z =" + z);

// z=435.00

Conversioni e approssimazioni

• Le classi BigInteger e BigDecimalappartengono al pacchetto java.math e pertanto devono essere importate:import java.math.BigDecimal;

import java.math.BigInteger;

• Si potrebbe anche scrivere:java.math.BigDecimal x = new

java.math.BigDecimal("4.35");

ma è uno stile poco usato (solitamente si utilizza import e si scrive solo la classe).

Page 36: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

36

Costanti

L’uso delle costanti

• Questo programma effettua un cambio di valuta

• Un utente potrebbe chiedersi quale sia il significatodel numero 0.71 usato nel programma, ma anche se questo valore non varierà nel tempo.

public class Convertimonete {

public static void main(String[] arg){

double dollaro = 2.35;

double euro = dollaro * 0.71;

}

}

L’uso delle costanti

• Così come si usano nomi simbolici descrittivi per le variabili, è opportuno assegnare nomi simbolici anche alle costanti utilizzate nei programmi. (par. 4.2)

• Si hanno dei vantaggi:1. si aumenta la leggibilità

2. si evitano molte sostituzioni, se il valore della costante deve cambiare

3. non lo si confonde con altri valori.

L’uso delle costanti

1. Aumenta la leggibilità: chiunque usi il nostro programma capisce che 0.71 è il fattore di conversione

public class Convertimonete1 {

public static void main(String[] arg){

final double EURO_DOLLARO = 0.71;

double dollaro = 2.35;

double euro = dollaro*EURO_DOLLARO;

}

}

Page 37: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

37

L’uso delle costanti

2. Si evitano molte sostituzioni: il valore può cambiare e lo dobbiamo cambiare in ogni istruzione in cui viene usato:

public class Convertimonete2{

public static void main(String[] arg){

final double EURO_DOLLARO = 0.90;

double dollaro1 = 2.35;

double euro1 = dollaro1*EURO_DOLLARO;

double dollaro2 = 3.45;

double euro2 = dollaro2*EURO_DOLLARO;

}

}

L’uso delle costanti

3. Si può confondere con altri valori:

public class Convertimonete3{

public static void main(String[] arg){

final double EURO_DOLLARO = 0.75;

double dollaro1 = 2.35;

double euro1 = dollaro1*EURO_DOLLARO;

double costocaffe = 0.90;

}

}

Definizione di costante• Sintassi.

final nometipo NOME_COSTANTE =

espressione;

• NOME_COSTANTE è il nome che vogliamo dare alla costante

• In Java si usa la seguente convenzione: dare alle costanti un nome usando tutte le lettere maiuscole (es. MAX_VALUE nei tipi numerici)

• I nomi composti si ottengono attaccando le parole successive alla prima con un carattere di sottolineatura.

Definizione di costante

• Le costanti sono identificate dalla parola chiave final.

• In fase di definizione si deve specificare il tipo della costante ed attribuire un valore

(espressione): tale valore non può più essere

modificato.

• Il tentativo di modificare il valore della costante, dopo l’inizializzazione, produce un errore (semantico) durante la compilazione.

Page 38: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

38

Struttura iterativa

Struttura iterativa

• Sia P un predicato (condizione); nel caso in cui P sia vero vogliamo eseguire ripetutamente un gruppo di <istruzioni>, che non dovrà più essere eseguito nel caso in cui P sia falso.

fintantoché P eseguire <istruzioni> //P vero

//fine ciclo

// dopo la fine della struttura P è falso

Struttura iterativa

• Problema. Stampare i primi cinque numeri naturali in ordine decrescente.

• Analisi. Dobbiamo ripetere la stampa di un numero, che varia in un intervallo di valori:

1. individuare il predicato P• fino a quando si prosegue

2. individuare le istruzioni da ripetere• cosa dobbiamo fare

Struttura iterativa

• Quali sono i numeri da stampare?• 1, 2, 3, 4, 5 ma nell’ordine inverso:

5, 4, 3, 2, 1• Possiamo pensare di partire dal più grande (5) e ad

ogni iterazione calare di una unità, quindi l’iterazione sarà:

stampa numeroesegui numero-1

• Quando ci fermiamo? Lo 0 non è compreso, quindi fintantoché numero è maggiore di zero, ripetiamo le istruzioni.

Page 39: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

39

Struttura iterativa

• Progetto.algoritmo stamparovescia

variabili a intero

a ←←←← 5

finché a > 0 eseguire

stampa a

a ←←←← a-1

//fine struttura

• Questa struttura termina?

Struttura iterativa

• Scriviamo i valori che la variabile a assume durante il funzionamento dell’algoritmo:

valore predicato stampaa > 0

a = 5 V 5a = 4 V 4a = 3 V 3a = 2 V 2a = 1 V 1a = 0 F il ciclo termina

Struttura iterativa

• Osserviamo che il ciclo è stato eseguito 5 volte e che il predicato è stato valutato 6 volte:

5 vero + 1 falso

• Qual è il comportamento di un ciclo “finché”?

• Tale ciclo:• può non essere mai eseguito

• può essere eseguito una o più volte

• deve terminare.

Struttura iterativa

• Si deve fare molta attenzione quando si scrivono i cicli, perché si possono introdurre gravi errori.

• Cosa cambia se iniziamo con a = -5 ?• Il predicato a > 0 è falso e quindi il ciclo non

viene mai eseguito. • Se quello che volevamo era la stampa dei

numeri, questo è un errore logico: il compilatore non segnalerà errore ma il programma non eseguirà le operazioni richieste.

Page 40: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

40

Struttura iterativa

• Cosa cambia se scriviamo a ← a+1?• I valori da a saranno: 5, 6, 7, … il predicato

sarà sempre vero e il ciclo non termina. Questo è un errore logico grave.

• Un ciclo che non termina è (nei nostri programmi) sempre errato.

• Nell’iterazione ci deve sempre essere una istruzione in grado di modificare il predicatoe che può renderlo falso.

Struttura iterativa

• L’enunciato while. (par. 6.1)• Sia P un predicato, la sintassi è:

while (P)

istruzione;

while (P){//blocco

. . . . .

istruzione;

. . . .

}

finché P eseguire

iterazione

fine ciclo

Struttura iterativa

• Esempio. Scrivere un algoritmo per stampare i numeri dispari compresi tra 1 e 10.//inizio algoritmo

int i = 1;

while(i <= 10) {

System.out.println(i);

i = i+2;

}

• Verifica: i assume i valori 1, 3, 5, 7, 9, con predicato vero; quando i = 11 il predicato è falso e il ciclo termina.

Struttura iterativa• Il ciclo precedente è del tipo://definizione delle variabili indice,

// inizio, …

indice = inizio;

while(indice <= fine){

//iterazione;

indice = indice + passo;

}

• Questo ciclo è governato da un’unica variabile (indice) che descrive un intervallo di valori e che è incrementata di una quantità fissa(passo).

Page 41: Costruire oggetti - MathUniPD//le nuove coordinate del punto //saranno (3, 2) 4 Metodi che agiscono su oggetti • Il metodo getX restituisce un valore di tipo double. • Un metodo

41

Struttura iterativa

• L’enunciato for . (par. 6.2)• La sintassi è:

for (inizializzazione; controllo;incremento)

iterazione;

• L’indicazione dell’incremento della variabile i appartiene all’intestazione della struttura e non deve più essere scritta all’interno della iterazione.

Struttura iterativa

• Nel caso in cui nel corpo della struttura iterativa ci sia più di una istruzione, si inserisce una coppia di parentesi graffe per contenere il blocco di istruzioni.

for (inizializzazione; controllo; incremento)

{//inizio ciclo

//blocco di istruzioni

}//fine ciclo

Struttura iterativa

• Nel caso precedente il ciclo while si trasforma in: (par. 6.2)

for(indice = inizio; indice <= fine;

indice = indice + passo)

iterazione;

• Oppure se ci fossero più istruzioni da eseguire:for ( . . . ){

//blocco di istruzioni

}

Struttura iterativa

• In entrambe queste strutture (while e for) la condizione viene verificata all’inizio: entrambi questi cicli possono non essere mai eseguiti.

• Nel ciclo for l’incremento della variabile i che governa il ciclo viene fatto alla fine della iterazione: • i=1, verifica condizione (i <= n): è vera, iterazione,

incremento di i che diventa 3; verifica condizione: èvera, iterazione, … , incremento di i che diventa 11; verifica condizione: è falsa; il ciclo termina.