Menu
CoddyTech

מקרה ומחלקות

חלק מהיחידה תכנות מונחה עצמים במסלול ה-Ruby של Coddy. שיעור 35 מתוך 57.

case יכולה לבצע הסתעפות לפי המחלקה של ערך. when Integer תואם לכל מספר שלם, כי case משווה באמצעות ===, ו-Integer === 5 בודק אם 5 הוא Integer (is_a?):

def describe(value)
  case value
  when Integer then "integer #{value}"
  when Float then format("float %.2f", value)
  when String then "text of #{value.size} chars"
  when nil then "nothing"
  else "other: #{value.class}"
  end
end

[5, 2.5, "hi", nil, [1, 2]].each { |v| puts describe(v) }

פלט:

integer 5
float 2.50
text of 2 chars
nothing
other: Array

מכיוון ש-=== במחלקה פועל לפי is_a?, ענף when עם מחלקת־על מתאים גם לתת־המחלקות שלה. סדרו את הענפים מהמחלקה הספציפית ביותר לכללית ביותר:

class Animal
end

class Dog < Animal
end

def kind(x)
  case x
  when Dog then "a dog"
  when Animal then "some animal"
  else "not an animal"
  end
end

puts kind(Dog.new)
puts kind(Animal.new)
puts kind("Rex")
puts Animal === Dog.new

פלט:

a dog
some animal
not an animal
true

ב־when אחד אפשר לציין כמה מחלקות, והענפים יכולים לבצע עבודה ממשית עם הערך, כמו חישוב הסכום של מבנה מקונן עם סוגים מעורבים:

def total(value)
  case value
  when Integer, Float then value
  when String then value.to_f
  when Array then value.sum { |v| total(v) }
  when Hash then total(value.values)
  else 0
  end
end

puts total([1, "2.5", { a: 3, b: [4, nil] }])

פלט:

10.5

התניה לפי מחלקות מתאימה לערכים שלמחלקות שלהם אי אפשר להוסיף מתודות חדשות, כמו מספרים, מחרוזות ומערכים, או נתונים שמגיעים מבחוץ. במחלקות משלך, העדף פולימורפיזם: מחלקה חדשה דורשת מתודה חדשה, ולא ענף חדש בכל case:

# מחלקות משלך: תן לכל אחת לענות
shape.area

# ערכים מובנים שמגיעים מבחוץ: הסתעף לפי המחלקה
case value
when Integer then ...
when String then ...
end
challenge icon

אתגר

קל

השלם את פונקציית העזר describe(value) בקובץ functions.rb באמצעות case על המחלקה של הערך. היא מחזירה integer 5 (odd) או integer 4 (even), את float 2.50 עם שתי ספרות אחרי הנקודה, את text "hi" (2 chars), את list of 3: 1, a, 2.5 (האלמנטים מחוברים באמצעות to_s), את nothing עבור nil ואת other Symbol עבור כל דבר אחר. סמלים הם הסוג הנוסף היחיד במבחנים.

הקוד שסופק ממיר כל שורת קלט לערך (מספרים שלמים, מספרים עשרוניים, רשימות [a,b], הערך nil, סמלים מהצורה :name, או טקסט) ומדפיס את describe עבור כל אחד מהם.

הקוד שלך צריך להופיע ב־functions.rb. הקובץ main.rb מכיל את קוד הקלט/פלט שסופק ואי אפשר לערוך אותו.

נסו בעצמכם

require_relative 'functions'

# קוד הקלט/פלט שסופק: יש להשאיר אותו כפי שהוא
input = []
while (line = gets)
  input << line.chomp
end
def parse(text)
  return Integer(text) if text.match?(/\A-?\d+\z/)
  return Float(text) if text.match?(/\A-?\d+\.\d+\z/)
  return nil if text == "nil"
  return text[1..].to_sym if text.start_with?(":")
  return text[1...-1].split(",").map { |t| parse(t) } if text.start_with?("[")

  text
end

input.each { |line| puts describe(parse(line)) }
quiz iconבחנו את עצמכם

השיעור הזה כולל חידון קצר. התחילו את השיעור כדי לענות עליו ולעקוב אחרי ההתקדמות.

כל השיעורים ביחידה תכנות מונחה עצמים

תרגלו בעצמכם: קומפיילר Ruby אונליין