Ereditarietà
Prof. Francesco Scarcello
D.E.I.S., Università della Calabria
Corso di Informatica 2
Esempio: il conto bancario
public class BankAccount
{
public BankAccount() { balance = 0;}
public BankAccount(double initialBalance)
{
balance = initialBalance;}
public void deposit(double amount)
{
balance = balance + amount;}
public void withdraw(double amount)
{
balance = balance - amount; }
public double getBalance(){return balance;}
public void transfer(BankAccount other,
double amount)
{
withdraw(amount);
other.deposit(amount);}
private double balance;
}
1
Estendere il codice
z Supponiamo di voler implementare altri
tipi di conto bancario.
z Per esempio, consideriamo un conto
bancario che dia interessi ad un certo
tasso fisso interestRate.
z Dobbiamo riscrivere tutto il codice?
z Possiamo sfruttare il codice esistente
estendendolo opportunamente?
La classe SavingsAccount
public class SavingsAccount extends BankAccount
{
public SavingsAccount(double rate)
{ interestRate = rate;
}
public void addInterest()
{ double interest = getBalance() * interestRate / 100;
deposit(interest);
}
private double interestRate;
}
2
Oggetti della sottoclasse
SavingsAccount
…
SavingsAccount s = new SavingsAccount(10);
s.deposit(1000);
…
3
Quando si estende una
classe...
z Si ereditano tutti i metodi e gli elementi di dati
della superclasse
z Si possono definire nuovi metodi
z Si possono definire nuovi elementi di dati
z Si possono ridefinire metodi per
specializzarne le funzionalità
Le regole del gioco
Una classe
y può estendere al più una classe
y può essere estesa da un numero arbitrario di
classi
Visibilità
y una sottoclasse può accedere ad elementi di
dati ed a metodi che siano public o protected
nella sua superclasse
4
Riferimenti ed assegnamento
SavingsAccount collegeFund = new SavingsAccount(10);
BankAccount anAccount = collegeFund;
Object anObject = anAccount;
SavingsAccount myFund = anAccount;
SavingsAccount yourFund = new BankAccount();
Una variabile di una classe C
può essere usata per riferirsi
agli oggetti di una qualunque
sottoclasse di C
Altri conti bancari
z Vogliamo un nuovo tipo di libretto di risparmio
che preveda interessi più alti, ma vincoli il
cliente a non prelevare denaro prima di un certo
tempo.
Eventuali prelievi anticipati vengono penalizzati.
z Inoltre vogliamo un conto corrente che
garantisca un certo numero di operazioni
gratuite. Le operazioni che eccedono tale soglia
sono soggette ad un costo.
5
public class TimeDepositAccount extends SavingsAccount
{ public TimeDepositAccount(double rate, int maturity)
{ super(rate);
periodsToMaturity = maturity; }
public void addInterest()
{ periodsToMaturity--;
super si usa per
accedere a dati e funzioni
della superclasse
super.addInterest();}
public void withdraw(double amount)
{ if (periodsToMaturity > 0)
super.withdraw(EARLY_WITHDRAWAL_PENALTY);
super.withdraw(amount); }
private int periodsToMaturity;
private static double EARLY_WITHDRAWAL_PENALTY = 20; }
public class CheckingAccount extends BankAccount
{
public CheckingAccount(int initialBalance)
{ super(initialBalance);
transactionCount = 0; }
public void deposit(double amount)
{ transactionCount++;
super.deposit(amount); }
public void withdraw(double amount)
{ transactionCount++;
super.withdraw(amount); }
public void deductFees()
{ if (transactionCount > FREE_TRANSACTIONS)
{ double fees = TRANSACTION_FEE *
(transactionCount - FREE_TRANSACTIONS);
super.withdraw(fees);}
transactionCount = 0;}
private int transactionCount;
private static final int FREE_TRANSACTIONS = 3;
private static final double TRANSACTION_FEE = 2.0;}
6
La gerarchia dei conti
correnti
La gerarchia dei rettili
antichi
7
Gerarchia di componenti per
la grafica
Polimorfismo
z Consideriamo la funzione transfer:
public void transfer(BankAccount other,
double amount)
{ withdraw(amount);
other.deposit(amount);}
z Ogni classe nella gerarchia eredita transfer
z Con quest’unica funzione possiamo
effettuare un trasferimento verso
qualunque tipo di conto corrente
8
BankAccount collegeFund = new BankAccount (10000);
CheckingAccount harrysChecking = … ;
…
collegeFund.transfer (harrysChecking, 1000);
Nota che other
è di tipo
BankAccount
Programma AccountTest.java
public class AccountTest
{
public static void endOfMonth(SavingsAccount savings)
{ savings.addInterest();
}
public static void endOfMonth(CheckingAccount checking)
{ checking.deductFees();
}
public static void printBalance(String name,
BankAccount account)
{ System.out.println(“Il saldo del conto ” + name
+ ” è di $” + account.getBalance());
}
9
Programma AccountTest.java (continua)
public static void main(String[] args)
{ SavingsAccount momsSavings = new SavingsAccount(0.5);
TimeDepositAccount collegeFund=new TimeDepositAccount(1,3);
CheckingAccount harrysChecking = new CheckingAccount(0);
momsSavings.deposit(10000);
collegeFund.deposit(10000);
momsSavings.transfer(harrysChecking, 2000);
collegeFund.transfer(harrysChecking, 980);
harrysChecking.withdraw(500);
harrysChecking.withdraw(80);
endOfMonth(momsSavings);
endOfMonth(collegeFund);
endOfMonth(harrysChecking);
printBalance(“Risparmi della mamma", momsSavings);
printBalance(“Fondo per il college", collegeFund);
printBalance(“Conto di Harry", harrysChecking);
} // Fine della funzione main
} // Fine della classe AccountTest
La superclasse universale
La classe Object costituisce la superclasse di
ciascuna classe Java
10
La classe Object
Alcune importanti funzioni definite in Object
(e quindi ereditate da ogni classe):
z public String toString();
z public boolean equals (Object ob);
z protected Object clone();
Clonazione di oggetti
BankAccount clonedAccount = anAccount.clone();
11
Il metodo Object.clone()
z Crea una copia superficiale
z Non può essere effettivamente invocato a meno
che non si implementi l’interfaccia Cloneable
12
Scarica

Ereditarietà Esempio: il conto bancario