קריאה ל־super
חלק מהיחידה תכנות מונחה עצמים במסלול ה-Ruby של Coddy. שיעור 24 מתוך 57.
בתוך מתודה שדורסת מתודה אחרת, super קוראת לגרסה של מחלקת-העל של אותה מתודה. תת-המחלקה יכולה להתבסס על התוצאה במקום לחזור עליה:
class Greeter
def greet(name)
"Hello, #{name}"
end
end
class LoudGreeter < Greeter
def greet(name)
super.upcase + "!"
end
end
puts LoudGreeter.new.greet("Ada")פלט:
HELLO, ADA!השימוש הנפוץ ביותר הוא initialize: מחלקת המשנה מקבלת ערך נוסף, מעבירה את הערכים המשותפים למחלקת העל באמצעות super(...) ושומרת את הערך שלה:
class Person
attr_reader :name, :age
def initialize(name, age)
@name = name
@age = age
end
end
class Student < Person
attr_reader :school
def initialize(name, age, school)
super(name, age)
@school = school
end
end
s = Student.new("Ada", 20, "MIT")
puts "#{s.name}, #{s.age}, #{s.school}"פלט:
Ada, 20, MITשלוש הצורות נבדלות בארגומנטים שהן מעבירות. super ללא סוגריים מעביר את אותם ארגומנטים שהמתודה הנוכחית קיבלה; super() לא מעביר ארגומנטים; super(a, b) מעביר בדיוק את אלה:
class Base
def show(*args)
"Base got #{args.inspect}"
end
end
class Child < Base
def show(a, b)
[super, super(), super(b)].join(" | ")
end
end
puts Child.new.show(1, 2)פלט:
Base got [1, 2] | Base got [] | Base got [2]super יכולה לפעול בכל מקום במתודה, או רק בתנאי מסוים. כאשר initialize של מחלקת המשנה מקבלת ארגומנטים אחרים מאלה של מחלקת האב שלה, super ללא ארגומנטים מעבירה את הארגומנטים הלא נכונים, וכתוצאה מכך מתקבלת לעיתים קרובות ArgumentError:
class Logger
def log(message)
puts "LOG #{message}"
end
end
class QuietLogger < Logger
def log(message)
super unless message.start_with?("debug")
end
end
logger = QuietLogger.new
logger.log("started")
logger.log("debug x=1")
logger.log("done")פלט:
LOG started
LOG doneאתגר
קלהשלם את המחלקות. Person מאחסנת את name ואת age, וה־to_s שלה מחזירה את Ada (36). Student מוסיפה בית ספר: ה־initialize שלה מעבירה את השם ואת הגיל ל־super, וה־to_s שלה מחזירה את Ada (20), studies at MIT, שנבנה מתוך super. Teacher מוסיפה מקצוע באותו אופן ומחזירה את Bo (45), teaches maths.
הקוד שסופק קורא שורות person Ada 36, student Ada 20 MIT או teacher Bo 45 maths ומדפיס כל אובייקט.
הקוד שלך צריך להופיע בקובצי person.rb, student.rb ו־teacher.rb. הקובץ main.rb מכיל את קוד הקלט/פלט שסופק ואי אפשר לערוך אותו.
נסו בעצמכם
require_relative 'person'
require_relative 'student'
require_relative 'teacher'
# קוד הקלט/פלט שסופק: יש להשאיר אותו כפי שהוא
input = []
while (line = gets)
input << line.chomp
end
input.each do |line|
kind, name, age, extra = line.split
person = case kind
when "student" then Student.new(name, age.to_i, extra)
when "teacher" then Teacher.new(name, age.to_i, extra)
else Person.new(name, age.to_i)
end
puts person
end
השיעור הזה כולל חידון קצר. התחילו את השיעור כדי לענות עליו ולעקוב אחרי ההתקדמות.
כל השיעורים ביחידה תכנות מונחה עצמים
3מתודות ומשתנים של מחלקה
מתודות של מחלקהמשתני מופע של מחלקהקבועיםמתודות ליצירת מופעיםסיכום – קודי קופוןתרגלו בעצמכם: קומפיילר Ruby אונליין