Nessun risultato. Prova con un altro termine.
Guide
Notizie
Software
Tutorial
  • Lezione 22 di 45
  • livello principiante
Indice lezioni

Ereditarietà multipla

Approfondimento sulle classi e sulla programmazione ad oggetti: l'ereditarietà multipla
Approfondimento sulle classi e sulla programmazione ad oggetti: l'ereditarietà multipla
Link copiato negli appunti

Ruby, di per sé, non permette l'ereditarietà multipla: ogni classe non può avere più di una superclasse. È possibile però aggirare questo "problema", che a detta di molti problema non è, attraverso l'utilizzo dei moduli e il meccanismo del mixin.

Oltre al classico utilizzo per la creazione di namespace, i moduli possono essere utilizzati per implementare una sorta di ereditarietà multipla. Vediamo innanzitutto cosa si intende per modulo e come si definisce.

I moduli sono dei contenitori di metodi, costanti e classi e, alla stessa maniera delle classi, devono avere un nome che inizia per lettera maiuscola. Sono definiti dalla parola chiave module; un esempio è il seguente:

module Net
    class HTTP
        def HTTP.get_print(uri_or_host, path = nil, port = nil)
           ...
        end
    end
end

Per poter accedere alle classi del modulo occorre importalo con l'istruzione require e poi fare riferimento alle classi con il nome esteso. Ad esempio se si vuole utilizzare il metodo get_print della classe HTTP del modulo Net occorre scrivere:

require 'net/http'
Net::HTTP.get_print 'www.google.com', '/index.html'

La creazione di un namespace permette sia di evitare problemi con i nomi, sia di rendere il codice più coerente e pulito. Oltre a ciò, come anticipato prima, è possibile utilizzare i moduli in maniera meno ortodossa ma molto efficace. Per ovviare alla mancanza dell'ereditarietà multipla basta racchiudere in un modulo i metodi che vogliamo "far ereditare" alla nostra classe e quindi includerlo con l'istruzione include. Di conseguenza possiamo utilizzare tutti i metodi del modulo dall'interno della nostra classe come dei normali metodi che vengono mescolati, mixed in appunto, a quelli definiti dalla classe e a quelli ereditati dalla superclasse.

Un esempio ci chiarirà tutto. Creiamo un semplice modulo con un solo metodo che non fa altro che stampare una frase a video:

module Inutile
    def hello
       "Saluti da #{self.class.name}"
    end
end

class Tokyo
    include Inutile
end

Istanziando una nuova classe possiamo chiamare il metodo hello ereditato dal modulo ottenendo:

> tk = Tokyo.new
> tk.hello
=> "Saluti da Tokyo"

In questo modo è possibile aggiungere alle classi una gran quantità di metodi senza nessuna fatica. Ad esempio possiamo dotare le nostre classi dei metodi di confronto includendo Comparable, o anche aggiungere dei metodi di ricerca e ordinamento includendo Enumerable e così via.

Ti consigliamo anche