Menu
CoddyTech

مُعيِّنات مخصّصة

جزء من قسم البرمجة كائنية التوجه في رحلة Ruby على Coddy. الدرس 8 من 57.

المُعيِّن هو أسلوب ينتهي اسمه بـ =. وكتابته بنفسك بدلًا من استخدام attr_writer يتيح له تنقية القيمة قبل تخزينها:

class Person
  attr_reader :name

  def name=(value)
    @name = value.strip.capitalize
  end
end

ada = Person.new
ada.name = "   aDA  "
puts "[#{ada.name}]"

الناتج:

[Ada]

يمكن للخاصية المعيِّنة أيضًا رفض قيمة عن طريق رفع خطأ. لا يُسنَد إلى متغير النسخة إلا إذا اجتازت القيمة التحقق، لذا يحتفظ الكائن بحالته القديمة:

class Product
  attr_reader :price

  def initialize(price)
    @price = price
  end

  def price=(value)
    raise ArgumentError, "price must be positive, got #{value}" if value <= 0

    @price = value
  end
end

item = Product.new(10)
begin
  item.price = -5
rescue ArgumentError => e
  puts e.message
end
puts item.price

الناتج:

price must be positive, got -5
10

يُرجع تعبير الإسناد دائمًا القيمة الموجودة على جانبه الأيمن، وليس ما يُرجعه المُعيِّن أو يخزّنه. اقرأ السمة مرة أخرى للاطّلاع على القيمة المخزّنة:

class Thermometer
  attr_reader :celsius

  def celsius=(value)
    @celsius = value.round
  end
end

t = Thermometer.new
result = (t.celsius = 21.7)
puts result
puts t.celsius

الناتج:

21.7
22

يوفّر القارئ والمُعيِّن المخصّص معًا سمةً يستطيع الكود الخارجي قراءتها وتغييرها، ولكن إلى قيم صالحة فقط. أبقِ التحقّق في المُعيِّن وحده، لكي يمرّ كل تغيير عبر القاعدة نفسها:

class Volume
  attr_reader :level

  def level=(value)
    raise ArgumentError, "level must be 0-10" unless (0..10).cover?(value)

    @level = value
  end
end
challenge icon

التحدي

سهل

أكمل الصنف Person. يزيل المُعيِّن name= المسافات حول القيمة ويجعل الحرف الأول من كل كلمة كبيرًا ( ada lovelace تصبح Ada Lovelace). يرفع المُعيِّن age= الاستثناء ArgumentError مع الرسالة invalid age: 200 عندما يكون العمر خارج النطاق من 0 إلى 150، وإلا فإنه يخزّنه. ويمكن قراءة كلتا القيمتين.

يبدأ كائن Person جديد بالاسم Unknown والعمر 0. يقرأ الكود المُزوَّد الأوامر name text أو age n، ويطبّقها باستخدام المُعيِّنات ويطبع الشخص بالشكل Ada Lovelace (36) بعد كل أمر، أو يطبع رسالة الخطأ عندما يرفض أحد المُعيِّنات القيمة.

ضع كودك في person.rb. يحتوي main.rb على كود الإدخال والإخراج المُزوَّد، ولا يمكن تعديله.

جرّب بنفسك

require_relative 'person'

# شيفرة الإدخال/الإخراج المقدَّمة: اتركها كما هي
input = []
while (line = gets)
  input << line.chomp
end
person = Person.new
input.each do |line|
  command, value = line.split(" ", 2)
  begin
    command == "name" ? person.name = value : person.age = value.to_i
    puts "#{person.name} (#{person.age})"
  rescue ArgumentError => e
    puts e.message
  end
end
quiz iconاختبر نفسك

يتضمن هذا الدرس اختبارًا قصيرًا. ابدأ الدرس للإجابة عليه وتتبّع تقدمك.

جميع دروس البرمجة كائنية التوجه

تدرّب بنفسك: مترجم Ruby عبر الإنترنت