Metody chronione
Część sekcji Programowanie obiektowe ścieżki Ruby w Coddy. Lekcja 18 z 57.
Metoda chroniona znajduje się pomiędzy publiczną a prywatną. Kod spoza klasy nie może jej wywołać, ale każdy obiekt tej samej klasy może wywołać ją na innym obiekcie. Dzięki temu dwa obiekty mogą porównywać dane, których nie ujawniają reszcie programu:
class Account
def initialize(owner, balance)
@owner = owner
@balance = balance
end
def richer_than?(other)
balance > other.balance
end
protected
def balance
@balance
end
end
ada = Account.new("Ada", 500)
bo = Account.new("Bo", 300)
puts ada.richer_than?(bo)
begin
ada.balance
rescue NoMethodError => e
puts e.message
endWynik:
true
protected method `balance' called for an instance of AccountRóżnica w porównaniu z private ujawnia się, gdy odbiorcą jest inny obiekt. other.balance działa w przypadku metody chronionej, a w przypadku prywatnej — nie:
class Sample
def initialize(n)
@n = n
end
def compare_protected(other)
other.guarded + guarded
end
def compare_private(other)
other.hidden + hidden
rescue NoMethodError
"private refused other.hidden"
end
protected
def guarded
@n
end
private
def hidden
@n
end
end
a = Sample.new(1)
b = Sample.new(2)
puts a.compare_protected(b)
puts a.compare_private(b)Wynik:
3
private refused other.hiddenprotected działa również z attr_reader, czyli typowym sposobem udostępniania wartości tylko obiektom jednej klasy, na przykład po to, by zdecydować, który z dwóch obiektów wygrywa:
class Player
attr_reader :name
def initialize(name, rating)
@name = name
@rating = rating
end
def stronger?(other)
rating > other.rating
end
protected
attr_reader :rating
end
a = Player.new("Ada", 1200)
b = Player.new("Bo", 1100)
puts a.stronger?(b)
puts [a, b].select { |pl| pl.stronger?(b) }.map(&:name).inspectWynik:
true
["Ada"]Wybierz najwęższy poziom, który działa. public dotyczy interfejsu klasy, protected danych, które obiekty tej klasy porównują ze sobą, a private wszystkiego innego:
public # każdy: order.total
protected # obiekty danej klasy: other.balance wewnątrz Account
private # tylko sam obiekt: subtotal, self.subtotalWyzwanie
ŁatwyUzupełnij klasę Account. Saldo może być odczytywane tylko przez inne konta: ustaw jego czytnik jako chroniony. richer_than?(other) porównuje salda, a transfer_to(other, amount) przekazuje pieniądze na inne konto za pomocą chronionej metody tego konta receive(amount) i zwraca true albo zwraca false, gdy saldo jest za niskie. to_s zwraca tylko imię właściciela.
Dostarczony kod odczytuje imiona i salda dwóch właścicieli, a następnie polecenia transfer a b 50, wypisując ok lub refused. Następnie wypisuje Ada is richer (albo Bo is richer, albo equal), a na końcu próbuje odczytać balance z zewnątrz, wypisując balance is protected, gdy Ruby odmówi.
Twój kod umieść w pliku account.rb. Plik main.rb zawiera dostarczony kod wejścia/wyjścia i nie można go edytować.
Spróbuj swoich sił
require_relative 'account'
# Dostarczony kod wejścia/wyjścia: pozostaw go bez zmian
input = []
while (line = gets)
input << line.chomp
end
accounts = input[0..1].map do |line|
owner, balance = line.split
Account.new(owner, balance.to_i)
end
a, b = accounts
input.drop(2).each do |line|
_, from, to, amount = line.split
source = from == "a" ? a : b
target = to == "a" ? a : b
puts source.transfer_to(target, amount.to_i) ? "ok" : "refused"
end
if a.richer_than?(b) then puts "#{a} is richer"
elsif b.richer_than?(a) then puts "#{b} is richer"
else puts "equal"
end
begin
a.balance
puts "balance is public"
rescue NoMethodError
puts "balance is protected"
end
Ta lekcja zawiera krótki quiz. Zacznij lekcję, żeby na niego odpowiedzieć i śledzić swoje postępy.
Wszystkie lekcje w sekcji Programowanie obiektowe
1Klasy i obiekty
Praca z plikamiDefiniowanie klasZmienne instancjiMetody i selfto_s i inspectPowtórzenie – karta biblioteczna4Hermetyzacja
Metody prywatneMetody chronionePrywatne setteryOchrona stanuPowtórzenie – automat vendingowy7Polimorfizm i typowanie kacze
PolimorfizmTypowanie kaczeMetody abstrakcyjnecase i klasyPowtórzenie – metody płatności10Wzorce projektowe, część 2
Delegowanie z ForwardableWzorzec dekoratoraWzorzec budowniczegoWzorzec stanu2Metody dostępowe i self
Gettery i setteryWłasne setteryself w metodachTożsamość i równośćPowtórzenie – lista kontaktów5Dziedziczenie
PodklasyNadpisywanie metodWywoływanie superis_a? i przodkowiePowtórka – lista płac pracowników8Metody specjalne
Równość i hashMetody operatorówIndeksowanie i dodawanieWłasne kolekcjePowtórka – ułamki11Projekt: Zarządzanie biblioteką
Książki i czytelnicyWypożyczanie książekPoćwicz samodzielnie: Kompilator Ruby online