Duck Typing
Fa parte della sezione Programmazione orientata agli oggetti del percorso Ruby di Coddy. Lezione 33 di 57.
Ruby non controlla la classe di un oggetto prima di chiamare un metodo; gli basta che l'oggetto abbia il metodo. «Se cammina come un'anatra e fa qua qua come un'anatra, è un'anatra.» Questo è il duck typing: classi che non condividono alcuna superclasse possono comunque essere usate nello stesso punto:
class Duck
def speak
"Quack"
end
end
class Robot
def speak
"Beep"
end
end
class Radio
def speak
"...news..."
end
end
[Duck.new, Robot.new, Radio.new].each { |thing| puts thing.speak }Output:
Quack
Beep
...news...Anche le classi integrate partecipano. Un metodo che usa solo << funziona con un array, una stringa o un tuo qualsiasi oggetto che definisce <<:
class Tally
attr_reader :count
def initialize
@count = 0
end
def <<(_item)
@count += 1
self
end
end
def export(items, target)
items.each { |item| target << item.to_s }
target
end
p export([1, 2], [])
p export([1, 2], +"")
puts export([1, 2, 3], Tally.new).countOutput:
["1", "2"]
"12"
3respond_to?(:name) chiede se un oggetto ha un metodo pubblico, senza chiamarlo. Usalo quando un oggetto potrebbe supportare o meno una funzionalità facoltativa:
class Printer
def print_page(text)
"printing #{text}"
end
end
class Scanner
end
[Printer.new, Scanner.new].each do |device|
if device.respond_to?(:print_page)
puts device.print_page("report")
else
puts "#{device.class} cannot print"
end
endOutput:
printing report
Scanner cannot printQuando l'oggetto non ha il metodo, la chiamata genera NoMethodError, il cui messaggio indica il metodo e l'oggetto. Il duck typing si basa sul fatto che ogni oggetto passato risponda ai metodi che gli vengono inviati:
def loudest(things)
things.map(&:speak).max_by(&:size)
end
class Cat
def speak
"Meow"
end
end
puts loudest([Cat.new, Cat.new])
begin
loudest([Cat.new, 42])
rescue NoMethodError => e
puts e.message
endOutput:
Meow
undefined method `speak' for an instance of IntegerSfida
FacileCompleta le classi Printer e LineCounter e la funzione di supporto export(items, target) in functions.rb. export invia ogni elemento al target con target << item.to_s e restituisce il target. Printer#<< stampa il testo con un numero di riga, 1: text, e restituisce la stampante. LineCounter#<< conta le righe e i caratteri e restituisce il contatore; il suo to_s restituisce 3 lines, 12 chars.
Il codice fornito legge gli elementi e li esporta in un array (stampato con p), in una nuova stringa (stampata con p), in un Printer e in un LineCounter (stampato con puts).
Il tuo codice va inserito in printer.rb, line_counter.rb e functions.rb. main.rb contiene il codice di input/output fornito e non può essere modificato.
Provalo tu
require_relative 'printer'
require_relative 'line_counter'
require_relative 'functions'
# Código de entrada/salida proporcionado: mantenlo tal como está
input = []
while (line = gets)
input << line.chomp
end
p export(input, [])
p export(input, +"")
export(input, Printer.new)
puts export(input, LineCounter.new)
Questa lezione include un breve quiz. Inizia la lezione per rispondere e tenere traccia dei tuoi progressi.
Tutte le lezioni di Programmazione orientata agli oggetti
1Classi e oggetti
Lavorare con i fileDefinire le classiVariabili d'istanzaMetodi e selfto_s e inspectRipasso - Tessera della biblioteca4Incapsulamento
Metodi privatiMetodi protettiSetter privatiProteggere lo statoRiepilogo - Distributore automatico7Polimorfismo e Duck Typing
PolimorfismoDuck TypingMetodi astratticase e classiRiepilogo - Metodi di pagamento10Pattern di progettazione Parte 2
Delegazione con ForwardablePattern DecoratorPattern BuilderPattern State2Metodi di accesso e self
Metodi di lettura e scritturaSetter personalizzatiself nei metodiIdentità e uguaglianzaRiepilogo - Elenco contatti5Ereditarietà
SottoclassiRidefinizione dei metodiChiamare superis_a? e antenatiRiepilogo - Paghe del personale8Metodi speciali
Uguaglianza e hashMetodi degli operatoriIndicizzazione e appendCollezioni personalizzateRiepilogo - Frazioni11Progetto: Gestione della biblioteca
Libri e iscrittiPrendere in prestito i libriEsercitati da solo: Compilatore Ruby online