משתנים ב Ruby שאפשר לגשת אליהם מכל מקום

04/02/2020

שפת רובי מציעה 3 דרכים לייצר משתנה גלובאלי - כלומר משתנה שאפשר לגשת אליו מכל מקום בתוכנית. הנה ה-3 בקצרה עם הצעה מתי להשתמש בכל דרך.

1. קבועים

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

קבוע ב Ruby נראה כמו משתנה אבל מתחיל באות גדולה, למרות שבדרך כלל נכתוב את כל שם הקבוע באות גדולה. רובי עצמה לא עושה מאמץ כדי למנוע מכם לשנות קבוע (ובגלל זה השם קצת מבלבל), אבל אנחנו מתכנתים טובים ולכן נשתדל לא לשנות קבועים.

התוכנית הבאה מגדירה קבוע מחוץ לפונקציה וניגשת אליו מתוך הפונקציה:

PASSWORDS = {
    'one' => 'secret',
    'two' => 'number'
}

def check_password(username, password)
  PASSWORDS.key?(username) && PASSWORDS[username] == password
end

2. משתנים גלובאליים

אם התחשק לכם לשנות את הקבועים שלכם תשמחו לשמוע שלרובי יש תמיכה במנגנון שנקרא משתנים גלובאליים אבל אף אחד לא באמת משתמש בו. משתנה גלובאלי ברובי מתחיל בסימן דולר, אפשר להגדיר אותו בכל מקום בתוכנית ולהשתמש בו מכל מקום אחר. מעט השימושים במשתנים אלה הם במשתנים הגלובאליים של השפה עצמה, לדוגמא המשתנה $_ יקבל בצורה אוטומטית מ gets כל פעם שהיא מופעלת את הערך האחרון שהיא קראה מהמשתמש.

התוכנית הבאה מגדירה משתנה גלובאלי ברובי ומשנה אותו מתוך פונקציה:

$count = 0

def tick
  $count += 1
end

tick
tick
tick
puts $count

והתוכנית הבאה נעזרת ב $_ כדי לחסוך משתנה:

while gets
  next if /^d/
  print
end

התוכנית תדפיס את כל השורות פרט לאלה שמתחילות ב d: תחילה היא לוקחת טקסט מהמשתמש באמצעות gets. הטקסט יישמר אוטומטית במשתנה הגלובאלי $_, לאחר מכן היא בודקת אם $_ מתאים לביטוי הרגולרי (ואם כן מדלגת לקרוא עוד שורה) ולבסוף מדפיסה את תוכן המשתנה $_. וכן אם זה נשמע לכם קצת כמו השראה מפרל אתם כנראה צודקים.

3. משתני מחלקה

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

class Ticker
  @count = 0

  class << self
    attr_accessor :count
  end
end

def tick
  Ticker.count += 1
end

tick
tick
tick
puts Ticker.count

מבנה זה נותן לנו את השליטה הטובה ביותר בקוד: במידת הצורך נוכל לכתוב לבד את פונקציות ה Setter וה Getter ולשלוט בגישה מבחוץ למשתנים הגלובאליים שלנו. בנוסף העובדה שכל משתנה מקבל תחילית של שם המחלקה שקשורה אליו עוזרת לסדר את המשתנים בתוך התוכנית.