L'ereditarietà
In generale, l'uso dell'ereditarietà dà luogo a una gerarchia di classi; nei linguaggi con ereditarietà singola, si ha un albero se esiste una superclasse "radice" unica di cui tutte le altre sono direttamente o indirettamente sottoclassi (come la classe Object nel caso di Java) o a una foresta altrimenti; l'ereditarietà multipla definisce invece una gerarchia a grafo aciclico diretto.
Uno dei maggiori vantaggi derivanti dall’uso dell’ereditarietà è la maggiore facilità nella manutenzione del software. Infatti, rifacendoci all’esempio dei mammiferi, se qualcosa dovesse variare per l’intera classe dei mammiferi, sarà sufficiente modificare soltanto l’oggetto padre per consentire che tutti gli oggetti figli ereditino la nuova caratteristica.
Sottolineando che si definisce oggetto figlio (child object) quello che eredita tutte o parte delle proprietà e dei metodi definiti nell’oggetto padre (parent object) è importante chiarire un aspetto importante quando si parla di caratteristiche ereditate. Non sempre, infatti, un determinato metodo definito nella classe padre può produrre risultati corretti e congruenti con tutte le classi figlie. Ad esempio, supponiamo di aver definito una classe padre denominata Uccello, dalla quale faremo derivare le seguenti classi figlie: Passerotto, Merlo e Pinguino.
Nella classe padre, avremo definito il metodo vola(), in quanto rappresenta un comportamento comune a tutti gli uccelli. In tal modo, secondo quanto si è detto in questo paragrafo, tutte le classi figlie non avranno la necessità di implementare tale metodo ma lo erediteranno dalla classe Uccello. Purtroppo, però, nonostante il pinguino appartenga alla categoria degli uccelli, è noto che esso non è in grado di volare, seppur provvisto di ali.
In questo caso, il metodo vola() definito nella classe Uccello, sicuramente valido per la stragrande maggioranza di uccelli, non sarà utile (anzi, sarà proprio sbagliato) per la classe Pinguino. Come comportarsi in questi casi?
In OOP, ogni oggetto derivante da una classe padre ha la possibilità di ignorare uno o più metodi in essa definiti riscrivendo tali metodi al suo interno. Questa caratteristica è nota come overriding.
Utilizzando la tecnica dell’overriding, la classe Pinguino reimplementerà al suo interno il metodo vola(), conservando, comunque, la possibilità di richiamare in qualunque momento, anche il metodo definito nella classe padre. In quest’ultimo caso si parlerà di overriding parziale.
Commenti
Posta un commento